java基础之第一阶段1

3.计算机分为硬件系统与软件系统4.软件系统分为系统软件与应用软件5.我们是面向互联网架构开发的后端开发工程师,负责软件或者网站的开发6.我们目前主要学习的开发语言是JAVA7.人机交互的方式:图形化界面 命令行的方式

2 环境的准备:

第一步:下载并安装JDK8第二步:配置环境变量:配置哪个JDK,哪个就生效1)JAVA_HOME 配置的是JDK的根目录C:\Program Files\Java\jdk1.8.0_2412)Path: 不需要新建,配置的是JDK的bin目录3)CLASSPATH ,需要新建,配置的是JDK的lib目录验证:只要win+R输入命令:java -version 出现版本信息就说明配置正确eclipse使用的版本没有关系,JDK是1.8就行

3 入门案例步骤分析:

1.创建java project ,名字:day0112.创建package包,名字:cn.tedu.hello2->全小写,域名倒着写,单词直接用点隔开3.创建class类,名字:HelloWorld2->驼峰命名法,每个单词的首字母都要大写4.创建main()->main(),alt+/补全代码5.添加打印语句syso,英文双引号里是我们想要打印的内容:“快速掌握入门案例~”6.保存Ctrl + S 执行Ctrl+F11 Ctrl+Fn+F11

4 拓展知识

入门案例解析:/**

  • package --包

  • cn.tedu.hello -- 包名,全小写,公司的域名倒着写,单词之间用点隔开

  • ; -- 表示结束符

  • */package cn.tedu.hello;

/** *public --公共的,作为类的修饰符 *class --类,用于定义类的一个特殊的单词 *HelloWorld --类名,驼峰命名法,每个单词的首字母大写 *{ } -- 类的主体内容 *注意:{} () "" 都是成对出现的,而且都是英文符号 */public class HelloWorld { /** * public static void main(String[] args) {}--入口函数的标准写法 * public --公共的,作为main()的修饰符 * static --静态的 * void --空,无,表示这个方法没有返回值 * main --方法名 * () --表示这是一个方法 * String[] args--main()的固定写法 * {} -- 方法的主体内容 */ public static void main(String[] args) { /** * System --系统,表示要发出一个系统指令 * out -- 向外输出 * println() --如何输出/输出的方式:输出后换行 * print() --如何输出/输出的方式:输出后不换行 * "Hello world!"--向控制台输出的具体内容 * ;表示结束符 * */ System.out.print("Hello world!"); System.out.print("Hello world!"); System.out.print("Hello world!"); System.out.print("Hello world!"); System.out.print("Hello world!"); }}跨平台:一份代码,处处运行java语言是跨平台的,而不同系统安装不同的JVM,是java跨平台的前提

JDK:开发工具包-最大-开发必须安装JRE:运行时环境JVM:java虚拟机,负责加载并且运行.class字节码文件

DAY02

关键字 标识符 注释 变量 基本类型 类型转换

1 Java的标识符

由字母 数字 下划线 美元符号 组成不能以数字开头严格区分大小写见名之意,并且不要使用拼音或者中英文夹杂的方式不能使用关键字

2 关键字

被Java提前指定好的全小写单词,一共有50个2个保留字:const 与 goto ,目前还没有明确意义的关键字还有3个不可以用作标识符的单词:true false null

3 注释

用来解释代码,方便看看代码的人去理解代码的话

注释并不会影响程序的执行,会被编译器忽略掉单行注释: // 可以注释一行的内容多行注释:/ * * / 可以注释多行的内容文档注释:/** */ 也可以注释多行内容,还可以添加一些额外的信息,比如:作者/时间/版本…

4 数据类型

4.1 基本类型

4.2 引用类型

我们学习的是String字符串类型,这个类型的数据需要使用双引号包裹

5 案例中总结的经验:

静态数据想要与动态的变量名进行拼接,需要使用+号char字符型既可以保存单个字符,需要用‘ ’包裹,也可以保存数字,只不过数字会去查ASCII码表从控制台接受用户输入的数据:int a = new Scanner(System.in).nextInt();变量进行值交换,首先需要一个第三方变量协助交换,代码的格式:斜相对,首尾相连

6 变量定义

定义的时候并且赋值:变量的类型 变量名 = 变量值; 比如:int a = 19;先定义,后面再赋值:int a; a=99;注意:=是赋值符号,等号右边的值交给等号左边的变量来保存

7 类型转换

boolean类型不参与类型转换小转大,直接转 – 隐式转换大转小,强制转 – 显式转换,格式:byte b = (byte) a;浮变整,小数没 – 浮点型转整形是直接舍弃所有的小数部分的,不会四舍五入类型能否转换,取决于类型的取值范围,而不是字节数,字节数只能做大概的参考

8 5条字面值规则

整数默认为int类型小数默认为double类型byte short char 三种比int小的类型,可以使用范围内的值直接赋值字面值后缀:L F D字面值前缀:0b-2 0-8 0x-16

9 5条运算规则

运算结果的数据类型与最大类型保持一致3种比int小的类型,运算时会自动提升成int再运算整数运算溢出的问题,一旦溢出,数据就错误了浮点数运算不精确浮点数的特殊值 Infinity NaN

DAY03 复习

1 运算符

普通的四则运算 + - * / 是不会改变变量本身的值的

如果想要改变变量本身的值,需要把表达式的结果重新赋值给变量int a = 1;System.out.println(a+5);//6System.out.println(a);//1,不会改变a

a = a+5;//将表达式的结果赋值给aSystem.out.println(a);//会改变a的值

取余%(求模 mod) : 取余数,如果整除,余数为0

自增自减运算符++ :表示变量本身的值+1 – : 表示变量本身的值-1前缀式:符号在前,先改变变量本身的值,再使用,比如打印,计算…后缀式:符号在后,先使用,再改变变量本身的值 int a = 1; System.out.println(++a);//2,符号在前,先自增,再打印 System.out.println(a);//2,上面已经自增过了

  
      int b = 1;
      System.out.println(b++);//1,符号在后,先打印,再自增
      System.out.println(b);//2,打印过后,自增成2
      
      int c = 1;
      System.out.println(--c);//0,符号在前,先自减,再打印
      System.out.println(c);//0,上面已经自减过了
      
      int d = 1;
      System.out.println(d--);//1,符号在后,先打印,再自减
      System.out.println(d);//0,打印过后,自减成0

比较运算符

!= == > < >= <= 比较的结果都是布尔类型的

逻辑运算符

&&:双与/短路与:逻辑与单与相同,全真才真,只不过增加了短路的效果||:双或/短路或:逻辑与单或相同,全假才假,只不过增加了短路的效果 /*与:全真才真/ System.out.println("测试单与:"); System.out.println(true & true);//t System.out.println(true & false);//f System.out.println(false & true);//f System.out.println(false & false);//f System.out.println("测试双与:"); System.out.println(true && true);//t System.out.println(true && false);//f System.out.println(false && true);//f System.out.println(false && false);//f /*或:全假才假/ System.out.println("测试单或:"); System.out.println(true | true);//t System.out.println(true | false);//t System.out.println(false | true);//t System.out.println(false | false);//f System.out.println("测试双或:"); System.out.println(true || true);//t System.out.println(true || false);//t System.out.println(false || true);//t System.out.println(false || false);//f

三目/三元运算符

格式:1 ?2 :3;1是表达式,若1真,取2,若1假取3赋值运算符= :是普通的赋值运算符,等号右边的值交给等号左边的变量来保存复合赋值运算符:+= -= *= /=,主要是可以简写&类型的自动转换sum += 30; 等效于 sum = sum+30;

2 流程控制

2.1 顺序结构

顺序结构从头到尾所有代码依次都会执行到可以解决输入 输出 计算等问题,但是不可以先做判断,再选择性的执行代码

2.2 分支结构

1 单分支结构

适合只有一个判断条件时使用,符合条件,执行大括号里的代码,不符合条件,大括号里的代码跳过

  
      /*单分支结构*/
      int a = 15;
      if(a>10) {//判断条件
          System.out.println(a);//如果判断条件的结果为true,才执行此行代码
      }

2 多分支结构

适合有两种情况时使用,符合条件,执行代码1,其他情况执行代码2

/多分支结构/ char gender = '男';//定义性别为男 if(gender == '男') { System.out.println("男生可以玩滑板"); }else { System.out.println("女生也可以玩滑板~"); }

3 嵌套分支结构

适合有多个条件时使用,else-if的个数没有限制,else可加可不加

if(判断条件1) { 如果符合判断条件1,执行此处代码1,如果不符合,继续向下判断条件2}else if(判断条件2) { 如果符合判断条件2,执行此处代码2,如果不符合,继续向下判断条件3}else if(判断条件3) { 如果符合判断条件3,执行此处代码3,如果不符合,继续向下判断}else { 如果以上条件都不满足,执行此处代码}package cn.tedu.review;

import java.util.Scanner;

/*本类用于分支结构的复习///需求:接收用户输入的身高与体重,判断BMI指数//BMI=体重(Kg)/身高*身高(m)//过轻:低于18.5//正常:18.5~22.9//偏胖:23~24.9//肥胖:25~29.9//重度肥胖:高于30//极度肥胖:高于40public class TestIf { public static void main(String[] args) { //1.提示并接收用户输入的身高和体重数据 System.out.println("请您输入身高数据(单位:m)"); double h = new Scanner(System.in).nextDouble(); System.out.println("请您输入体重数据(单位:kg)"); double w = new Scanner(System.in).nextDouble();

  
      //2.计算BMI指数:BMI=体重(Kg)/身高*身高(m)
      double bmi = w/(h*h);       
      //3.定义一个变量用来保存最终的结果
      String r = "";
      //4.根据算出的bmi指数,给r重新赋值
      if(bmi < 18.5) {
          r = "过轻";
      }else if(bmi <= 22.9) {
          r = "正常";
      }else if(bmi <= 24.9) {
          r = "偏胖";
      }else if(bmi <= 29.9) {
          r = "肥胖";
      }else if(bmi < 40) {
          r = "重度肥胖";
      }else {
          r = "极度肥胖";
      }
      
      //5.打印最终的结果
      System.out.println("您的BMI指数:" + bmi);
      System.out.println("您的体重属于:" + r);
  }

}

4 选择结构

switch(a){ case 1 : 操作1;break;【可选】 case 2 : 操作2;break;【可选】 case 3 : 操作3;break;【可选】 case 4 : 操作4;break;【可选】 default : 保底选项;【可选】}执行顺序:先拿着变量a的值,依次与每个case后的值做比较,如果相等,就执行当前case后的操作,若case后没有break,就绪继续执行下一个case后的操作,如果一直没有遇到break,就会发生穿透的现象,包括default

注意事项:

变量a支持的类型byte short char int String变量a的数据类型与case后value的数据类型必须一致如果没有添加break,并且又有case被匹配到,会发生穿透的现象,包括deafultcase的个数 是否加break 是否加default 完全根据自己的业务来决定如果添加了default保底选项,又没有任何一个case被匹配到,就会执行default后的语句一般我们习惯在每个case后加break【这个只是建议,具体还是根据业务来写】

5 循环结构

当你想多次重复干某件事的时候,可以使用循环结构注意事项:开始条件只会在第一轮执行一次,剩下两个条件才会执行多次如果想了解for循环执行的具体步骤,可以参考Debug的笔记

Eclipse中的Debug笔记普通for循环

for(开始条件 ; 循环条件 ; 更改条件){ 循环体}注意1:写法小窍门:从哪开始 到哪结束 循环变量如何变化注意2:for循环能够执行多少次,取决于循环变量可以取到几个值

day04

数组

1.1 静态创建

int[] a = {1,2,3,4,5};int[] a = new int[]{1,2,3,4,5};

1.2 动态创建

int[] a = new int[5];

3 数组的创建过程

在内存中开辟连续的空间,用来存放数据给数组完成初始化过程,给每个元素赋予默认值数组完成初始化会分配一个唯一的地址值把唯一的地址值交给引用类型的变量a去保存如果想要操作数组中的元素,可以根据变量保存的地址找到数组,然后根据下标来操作数组的具体元素数组名保存的是数组的地址值,不是数组中每一个具体的元素,数组名是一个引用类型的变量

数组的特性

数组的长度通过数组名.length;来获取数组一旦创建,长度无法改变数组的下标从0开始,最大下标为数组长度-1如果访问到了不存在的下标,会数组下标越界异常

数组的工具类Arrays

toString(数组名),除了char类型以外,其他类型的数组想要查看数组的具体元素,都得使用这个方法,如果不用,打印是数组的地址值sort(数组名),给数组进行排序copyOf(要复制的数组,新数组的长度)如果新的长度大于原数组的长度–数组的扩容如果新的长度小于原数组的长度–数组的缩容如果新的长度等于原数组的长度–普通的复制注意:不管是什么长度,都不是修改原数组,而是创建新数组

数组的遍历

如果只是想查看数组中有哪些元素,直接使用System.out.println(Arrays.toString(方法名));就可以如果想要拿到数组中的一个个的具体元素,或者是对数组中的元素做进一步的操作,就需要对数组进行遍历遍历:把数组中的所有元素,从头到尾逐个“过一遍”通过循环遍历数组,所以循环中的循环变量代表的是数组的下标public class ReviewDemo {public static void main(String[] args) { int[] a = new int[10]; for(int i = 0;i<a.length;i++) { //System.out.println(i);//打印的是数组的下标0-9 a[i] = i+11;//a[i]代表的是数组中每一个具体的元素 } System.out.println(Arrays.toString(a)); //[11, 12, 13, 14, 15, 16, 17, 18, 19, 20]}}

冒泡排序

冒泡排序详细笔记排序思路:要比较多轮,每轮两个相邻的元素做比较,位置不对就互换代码思路:通过嵌套for循环来完成

外层循环:控制的是轮数,如果有n个数,最多n-1轮内层循环:控制的是每轮中比较的次数,每一轮的次数会递减,之前轮确定的最大值不应该参与后面轮的比较注意:外层循环的循环变量代表的是轮数1 2 3 4…内层循环的循环变量代表的是数组的下标[0,a.length-i)

DAY05 复习

数组

1.1 静态创建

int[] a = {1,2,3,4,5};int[] a = new int[]{1,2,3,4,5};

1.2 动态创建

int[] a = new int[5];

3 数组的创建过程

在内存中开辟连续的空间,用来存放数据给数组完成初始化过程,给每个元素赋予默认值数组完成初始化会分配一个唯一的地址值把唯一的地址值交给引用类型的变量a去保存如果想要操作数组中的元素,可以根据变量保存的地址找到数组,然后根据下标来操作数组的具体元素数组名保存的是数组的地址值,不是数组中每一个具体的元素,数组名是一个引用类型的变量

数组的特性

数组的长度通过数组名.length;来获取数组一旦创建,长度无法改变数组的下标从0开始,最大下标为数组长度-1如果访问到了不存在的下标,会数组下标越界异常

数组的工具类Arrays

toString(数组名),除了char类型以外,其他类型的数组想要查看数组的具体元素,都得使用这个方法,如果不用,打印是数组的地址值sort(数组名),给数组进行排序copyOf(要复制的数组,新数组的长度)如果新的长度大于原数组的长度–数组的扩容如果新的长度小于原数组的长度–数组的缩容如果新的长度等于原数组的长度–普通的复制注意:不管是什么长度,都不是修改原数组,而是创建新数组

数组的遍历

如果只是想查看数组中有哪些元素,直接使用System.out.println(Arrays.toString(方法名));就可以如果想要拿到数组中的一个个的具体元素,或者是对数组中的元素做进一步的操作,就需要对数组进行遍历遍历:把数组中的所有元素,从头到尾逐个“过一遍”通过循环遍历数组,所以循环中的循环变量代表的是数组的下标public class ReviewDemo {public static void main(String[] args) { int[] a = new int[10]; for(int i = 0;i<a.length;i++) { //System.out.println(i);//打印的是数组的下标0-9 a[i] = i+11;//a[i]代表的是数组中每一个具体的元素 } System.out.println(Arrays.toString(a)); //[11, 12, 13, 14, 15, 16, 17, 18, 19, 20]}}

冒泡排序

冒泡排序详细笔记排序思路:要比较多轮,每轮两个相邻的元素做比较,位置不对就互换代码思路:通过嵌套for循环来完成

外层循环:控制的是轮数,如果有n个数,最多n-1轮内层循环:控制的是每轮中比较的次数,每一轮的次数会递减,之前轮确定的最大值不应该参与后面轮的比较注意:外层循环的循环变量代表的是轮数1 2 3 4…内层循环的循环变量代表的是数组的下标[0,a.length-i)

DAY06 复习

面向过程:

这种编程思想强调的是过程,凡事亲力亲为

面向对象:

这种思想强调的是结果,面向对象是Java极其重要的特征,Java就是一门面向对象的语言我不在意是怎么完成的,我在意的是有对象可以帮我干活比如:我们想吃饭,不在意是哪个厨师做的,也不在意是哪个骑手送的,只要有厨师做,有骑手派送就好了我们可以把OOP的思维理解成一种行为习惯 思维方式比如衣服,没有办法给出一个明确的定义,但是,只要我们看到任何一件衣服,我们就自动把它归类到衣服这个分类中,因为你在过去的生活经验中已经见过太多的衣服,积累经验

3.类

类指的是类型Type,是指一类事物,使用Java中的class关键字来描述类是抽象的,要提取这一类事物的特征与功能可以把类理解成设计图纸,模板注意:类在现实世界中不是真实存在,它只是一种对象的数据类型

4.对象

对象就是根据类创建出来的一个个独立且具体的实例一个类可以创建出多个对象,我们通过对象唯一的地址值区分不同的对象对象具有各种特征,并且每个对象的每个特征都可以有自己特定的值对象具有各种行为,每个对象可以执行的操作

5.对象创建过程分析

Phone p = new Phone();创建对象时,内存发生了什么?

在栈内存中开辟一块空间,Phone类型的引用类型变量p,把p压入栈底,此时p只有一个默认值null在堆内存中开辟一块空间用于存放Phone类型的对象要给这个对象进行初始化,比如:String brand = null;此对象已经准备好,所以会生成一个唯一的地址值,并将这个地址值交给栈内存中的变量p来保存如果后续想要对对象做操作,比如:p.price=88.8;先会找到栈中p变量保存的地址值,根据这个地址找到堆中的对象再做进一步的操作

3.面向对象的特征–封装

3.1为啥要用封装?

封装可以提高程序的安全性封装可以让资源按照我们预先规定的方式来操作

3.2属性的封装

用private修饰属性,一旦属性被private修饰,就只能在本类中使用,外界无法访问所以为了让外界能够按照我们提供的方式来调用,需要根据属性生成公共的getXxx()与setXxx()方法

3.2 方法的封装

方法的封装也是使用private来修饰方法如果想要调用私有方法的功能,就需要在本类的公共方法里调用这个私有方法

DAY07 复习

1.构造函数:

格式:与本类类名同名,且没有返回值类型作用:创建对象,创建一次,执行一次构造函数分类:1)无参构造:默认存在,如果添加了其他构造,默认的构造函数会被覆盖2)含参构造:对于参数没有任何要求,有参数就行3)全参构造:全参构造的参数必须与本类属性一致全参构造不仅可以创建对象,还可以给对象的所有属性赋值

2.构造代码块:

位置:类里方法外执行时机:每次创建对象时执行,并且优先于构造方法执行作用:用于提取所有构造方法的共性功能

3.局部代码块:

位置:方法里执行时机:调用本局部代码块所处的方法时执行作用:用于控制变量的作用范围

4.this的用法:

1.当成员变量与局部变量同名时,使用this指定成员变量2.使用this在构造方法的第一行调用构造方法的功能this();–调用的是本类的无参构造this(参数);–调用的是本类对应参数的构造方法

5.super的用法:

1.当父类的成员变量与子类的变量同名时,使用super指定父类的成员变量2.使用super在子类构造方法的第一行调用父类构造方法的功能

super();–调用的是父类的无参构造super(参数);–调用的是父类对应参数的构造方法

继承

继承的关键字extends 格式: 子类 extends 父类继承相当于子类把父类的功能复制了一份,包括私有资源Java只支持单继承:一个子类只能有一个父类,一个父类可以有多个子类继承具有传递性:爷爷的功能会传给爸爸,爸爸的功能会传给孙子子类只可以使用父类的非私有资源,私有资源不可用的原因是不可见子类可以拥有自己的特有功能继承是is a 强耦合的关系,依赖性非常强,比如我们看到”熊孩子”,就知道他有一个”熊父母”

方法的重写

前提:子类继承父类以后,对父类的功能做改进语法规则:两同 两小 一大两同:子类的方法与父类方法的方法名+参数列表相同一大:子类方法的修饰符 >= 父类方法的修饰符两小:子类方法的返回值类型 <=父类方法的返回值类型子类方法抛出的异常类型 <= 父类方法抛出的异常类型注意:我们在重写规则中提到的方法的返回值类型的大小,指的不是值的大小【1与2】,也不是字节的大小【byte与int】,我们这里指的“大小”是说:子类方法的返回值类型必须是父类方法返回值类型的子类或者是同一类型比如父类是:void,子类是void比如父类是:Cat,子类是MiaoMiao

DAY08 复习

1.继承中变量的使用

如果父类的成员变量与子类的成员变量同名时,使用super.变量名指定父类的成员变量

2.继承中构造方法的使用

我们每次创建对象的时候,都会先触发构造函数创建子类对象时,会先调用父类的无参构造,因为子类的构造函数中默认存在一个super();如果父类没有无参构造的话,我们就需要手动指定子类去调用父类的含参构造super(参数);构造方法不可以被继承,原因是:构造方法名必须是本类的类名,不可能在子类中存在一个父类名字的构造方法

3.方法的重写

重写:子类对父类的方法不满意时,可以重写父类的方法注意:重写是在不改变父类方法的前提下,实现功能的修改与拓展,重写后子类对象调用的就是重写后的功能原则:两同 两小 一大两同:方法名+参数列表相同一大:子类方法的修饰符权限 >= 父类方法的修饰符权限两小:子类方法的返回值类型,有两种选择:1)子类方法的返回值类型是父类方法的返回值类型的子类2)子类方法的返回值类型与父类方法的返回值类型相同比如:父:void 子:void父:int 子:int 但是:byte short long都不行!没有继承关系父:Animal 子:Animal/Cat都可以,但不可以是Car我们还可以给方法上加@Override注解,标记这是一个重写的方法package cn.tedu.review;/本类用于复习方法的重写///重写的原则://两同:方法名与参数列表//两小:方法的返回值类型 属于 父类方法返回值类型的子类/保持一致//一大:方法的修饰符 >= 父类方法的修饰符

public class TestExtends { public static void main(String[] args) { //4.创建两个类的对象 Father f = new Father(); Son s = new Son(); //5.1测试重写的方法第1组 f.eat(); s.eat(); //6.3测试重写的方法第2组 f.sleep(6); s.sleep(8); //7.3测试重写的方法第3组 int a = f.play(); System.out.println("从父类方法中接收到的返回值:"+a); int b = s.play(); System.out.println("从子类方法中接收到的返回值:"+b);

  
      //8.4试重写的方法第4组
      Animal a2 = f.getPet();
      System.out.println(a2.name);
      Dog d2 = s.getPet();
      System.out.println(d2.name);
  }

}//1.创建父类class Father{ //3.1添加父类的方法 public void eat(){ System.out.println("爸爸爱吃肉"); } //6.1添加父类的方法 public void sleep(int n){ System.out.println("爸爸晚上睡"+n+"个小时"); } //7.1定义父类中的方法 public int play(){ System.out.println("爸爸在玩风筝"); return 666; } //8.2定义父类中的方法 public Animal getPet(){ Animal a = new Animal(); return a; }}//2.创建子类class Son extends Father{ //3.2子类重写父类对应的方法 @Override public void eat(){ System.out.println("儿子爱吃蔬菜"); } //6.2添加子类重写的方法 @Override public void sleep(int n){ System.out.println("儿子要睡"+n+"个小时"); } //7.3重写父类的方法 public int play(){ //public long play(){//报错:long与int没有继承关系 System.out.println("儿子在玩游戏"); return 999; } //8.3重写父类中的方法 //写法一:父子类的返回值类型一致// public Animal getPet(){// Animal a = new Animal();// return a;// } //写法二:子类方法的返回值类型是父类方法返回值类型的子类 @Override public Dog getPet(){ Dog d = new Dog(); return d; }

}//8.1准备两个辅助测试的类class Animal{ String name = "啥动物都行";}class Dog extends Animal{ String name = "小狗";}

4.静态:

1.static可以修饰成员变量和方法2.被static修饰的资源称为静态资源3.静态资源随着类的加载而加载,最先加载,优先于对象进行加载4.静态资源可以通过类名直接调用,也被称作类资源5.静态被全局所有对象共享,值只有一份6.静态资源只能调用静态资源7.静态区域内不允许使用this与super关键字

5.静态代码块static{}

格式:static{ }位置:类里方法外执行时机:随着类的加载而加载,优先于对象进行加载【只加载一次】作用:用于加载那些需要第一时间就加载,并且只加载一次的资源,常用来初始化顺序:静态代码块 构造代码块 构造方法 普通方法【如果普通方法里有局部代码块,执行局部代码块】TIPS: 如果有多个静态资源,加载顺序取决于先后位置TIPS: 静态不可以与this和super共用

6.final 关键字

修饰类:最终类,不可以被继承修饰方法:这个方法的最终实现,不可以被重写修饰常量:值不可以被更改,并且常量定义时必须赋值注意:常量的定义需要使用全大写,单词之间使用下划线分隔

7.重写与重载的比较:

重载:在一个类中的现象:同一个类中,存在方法名相同,参数列表不同的方法重写:是指建立了继承关系以后,子类对父类的方法不满意,可以重写,遵循两同两小一大原则重载的意义:是为了外界调用方法时方便,不管传入什么样的参数,都可以匹配到对应的同名方法重写的意义:在不修改源码的情况下,进行功能的修改与拓展

DAY09 复习

1 面向对象之多态

  1. 前提:继承+重写

  2. 口诀1:父类引用指向子类对象解释:父类类型的引用类型变量保存的是子类类型的对象的地址值

  3. 口诀2:编译看左边,运行看右边解释:编译时要看父类是否定义了这个资源,运行时使用的是子类的功能

  4. 资源使用情况成员变量使用的是父类的 成员方法使用的是父类的方法定义,子类的方法体 如果多态对象调用的是子类没有重写过的方法,方法定义与方法体使用的都是父类的,所以这个不符合多态的前提,直接使用纯纯的父类对象调用即可 静态资源属于类资源,随着类的加载而加载,只会加载一次,优先于对象进行加载,可以通过类名直接调用,被全局所有对象共享,所以静态不存在重写的现象,在哪个类定义,就属于哪个类的资源 我们现在学习的多态,把自己看作是父类类型,参考“花木兰替父从军” 2 异常

  5. 异常的继承结构异常层次结构中的根是Throwable Error:目前我们编码解决不了的问题 Exception:异常 编译异常:未运行代码就报错了,强制要求处理 运行时异常:运行代码才报错,可以通过编译,不强制要求处理

2.异常的解决方案

  1. 捕获处理try-catch–自己解决异常捕获处理的格式:

try{ 可能会抛出异常的代码 }catch(异常的类型 异常的名字){ 万一捕获到了异常,进行处理的解决方案 }try-catch结构可以嵌套,如果有多种异常类型需要特殊处理的话使用多态的思想,不论是什么子异常,统一看作父类型Exception做出更加通用的解决方案,甚至可以只写这一个

2.向上抛出throws–交给别人解决

异常抛出的格式:在方法的小括号与大括号之间,写:throws 异常类型如果有多个异常,使用逗号分隔即可

private static void method3() throws ArithmeticException,InputMismatchException,Exception{ }

private static void method3() throws Exception{ }如果一个方法抛出了异常,那么谁来调用这个方法,谁就需要处理这个异常,这里的处理也有两种方案:捕获解决 或者 继续向上抛出不能直接把异常抛给main(),因为调用main()是JVM,没人解决了,该报错还报错,所以我们一般会在main()调用之前将异常解决掉

抽象

1.抽象类被关键字abstract修饰的类是抽象类一旦一个类中包含了抽象方法,那么这个类必须被声明成一个抽象类抽象类中的方法不做限制,非常自由:全普 / 全抽 / 半普半抽抽象类不可以实例化–创建对象抽象类有构造方法,它自己不用,但是为了子类创建对象时调用如果一个子类继承了抽象父类,那么有两种解决方案:1)作为一个抽象子类:不实现/实现部分抽象父类的抽象方法,躺平2)作为一个普通子类:需要实现抽象父类的全部抽象方法,还债2 抽象方法被关键字abstract 修饰的方法就是抽象方法抽象方法没有方法体{ },直接以分号结束3 练习1package cn.tedu.exec;/本类用于OOP综合练习1/public class TestAnimal { public static void main(String[] args) { //创建蚂蚁类的对象--子类对象 Ant a = new Ant(); //创建蜜蜂类的对象--子类对象 Bee b = new Bee(); a.fly();//调用子类的特有方法 a.layEggs();//调用子类继承的方法 b.makeHoney();//调用子类的特有方法 b.layEggs();//调用子类继承的方法 }}//1.抽象形成一个父类abstract class Animal{ //2.创建属性 int legNumbers;//腿的数量 int eggNumbers;//下蛋的数量 //3.创建下蛋的功能 public abstract void layEggs();}//4.创建子类蚂蚁类class Ant extends Animal{ //4.2添加子类的特有属性 int eggNumbers = 2;//蚂蚁一次产2个卵 //4.1创建子类的特有功能 public void fly(){ System.out.println("蚂蚁飞啦~"); } //4.3添加子类重写的方法 @Override public void layEggs(){ System.out.println("蚂蚁产卵的数量为:"+eggNumbers); }}//5.创建子类蜜蜂类class Bee extends Animal{ //5.2添加子类的特有属性 int eggNumbers = 10;//蜜蜂一次产10个卵 //5.1创建子类的特有功能 public void makeHoney(){ System.out.println("蜜蜂在产蜂蜜"); } //5.3添加子类重写的方法 @Override public void layEggs(){ System.out.println("蜜蜂产卵的数量为:"+eggNumbers); }}3 练习2-1 士兵类package cn.tedu.exec2;

import java.util.Random;

/OOP综合案例3-士兵类///1.定义士兵类public class Soldier { //2.定义士兵类的属性 int id;//士兵编号 int blood = 100;//默认血量值100 AK47 a;//引用类型AK47作为属性,相当于给士兵配枪,a的默认值是null

  //3.1定义士兵类的方法1
  public void go(){
      System.out.println(this.id+"号士兵在前进~");
  }
  //3.2定义士兵类的方法2
  public void attack(){
      //4.在攻击之前先判断这个士兵是否还活着,如果阵亡,直接结束当前攻击方法
      if(blood == 0){
          System.out.println("这是"+id+"号士兵的尸体。");
          return;/*直接结束当前方法attack()*/
      }
      System.out.println(id+"号士兵在进攻!");
      if(a != null){
          a.fire();//调用AK47发射子弹的开火方法
      }
      //1.生成一个随机数d,模拟进攻掉血的掉血量,随机数的范围是[0,10)
      int d = new Random().nextInt(10);//[0,10)
      blood = blood - d;//减去血量
  ​
      //2.血量最多减到0,如果出现负数,重置成0
      if(blood < 0){
          blood = 0;
      }
      //3.当血量为0时,说明士兵阵亡
      if(blood == 0){
          System.out.println(id+"号士兵已阵亡。");
      }
  ​
  }

}3 练习2-2 武器AK47类package cn.tedu.exec2;

import java.util.Random;

/OOP综合案例3-武器类/public class AK47 { //1.定义属性 int bullets = 100;//定义子弹的初始值为100发

  
  //2.1定义功能1--开火功能
  public void fire(){
      //2.1首先判断是否有子弹,如果没有子弹,直接结束当前方法
      if(bullets == 0){
          System.out.println("没有子弹了!!!");
          return;
      }
      //2.2生成一个随机值作为本次发射子弹的数量,范围:[0,10)
      int r = new Random().nextInt(10);
      //2.3判断实际子弹数是否够用,有多少发多少
      if(r>bullets){
          r = bullets;//将当前的实际子弹数赋值给随机数r
      }
      bullets = bullets -r;//发射子弹
      //2.4为了游戏效果,发射几发子弹就在控制台打印几个突
      for (int i = 0; i < r; i++) {
          System.out.print("突");//本轮打印的都在同一行
      }
      System.out.println("~");
      //2.5如果子弹数为0,提示用户弹夹空了
      if(bullets == 0){
          System.out.println("弹夹空了~");
      }
  }
  ​
  //2.2定义功能2--装载子弹的功能
  public void load(){
      bullets = 100;
      System.out.println("弹夹已装满");
  }

}4 练习2-3 测试类1

  
  package cn.tedu.exec2;
  ​
  import java.util.Scanner;
  ​
  /*本类用作士兵类的测试类*/
  public class TestDemo1 {
      public static void main(String[] args) {
          //1.新建AK47对象
          AK47 a = new AK47();
          System.out.println("按回车射击,输入load装载子弹");
          while(true){
              String s = new Scanner(System.in).nextLine();
              if(s.equals("load")){
                  a.load();
                  continue;
              }
              a.fire();
          }
      }
  }

4 练习2-4 测试类2

  
  package cn.cxy.exec2;
  ​
  public class TestDemo2 {
      public static void main(String[] args) {
          //新建 Soldier 士兵对象
          //内存地址,保存到变量s1
          Soldier s1 = new Soldier();
          Soldier s2 = new Soldier();
          //用s1引用第一个士兵对象
          //为它的id赋值
          s1.id = 9527;
          s2.id = 9528;
          //用s1找到第一个士兵对象
          //让第一个士兵执行go()方法代码
          s1.go();
          s2.go();
          //新建 AK47 对象,保存到s1.a
          s1.a = new AK47();
          s2.a = new AK47();
          s2.attack();
          s2.attack();
          s2.attack();
          s2.attack();
      }
  }

猜你喜欢

转载自blog.csdn.net/weixin_43762083/article/details/121607613