类
- 类可以用public final abstract修饰 或default
- 类名从可读性来说由一个或多个有意义的单词连缀成,单词首字母大写
- 静态成员不能直接访问非静态成员,只能创建对象去访问
- 一个没有编写构造器的类,系统会提供一个默认构造器
- 成员变量修饰符:public protected private static final default
- 可读性说,成员变量命名第一个单词首字母小写,后面单词首字母大写,单词单词间不使用间隔符
- 方法修饰符:public protected static final abstract default
- 方法命名与成员变量基本相同,但最好用动词开头
- static修饰成员表示属于类本身,而不属于单个实例,用来区分成员变量 方法 内部类 初始化块是属于类还是属于实例。
- static修饰的方法和成员变量既可以用类调用,也可以通过实例调用(会自动转换成类调用),非静态只能用实例调用。
- 构造器修饰符:public protected private
- 构造器名必须与类一样
对象
- 通过new关键字调用构造器创建这个类的对象
- 类名类型的变量实际上是一个引用,存放在栈内存中,指向存放在堆内存中类的对象
- java不允许直接访问堆内存中的对象,只能通过该对象的引用操作该对象
- 一个对象可以有多个引用
- 如果没有任何引用指向对象,那么程序无法再访问该对象,垃圾回收机制会回收该对象,释放所占内存区
- 切断对象与引用变量的联系,只需要将引用变量赋值为null
- this关键字总指向调用该方法的对象或该构造器正在初始化的对象,访问非静态成员时就不需要重新创建对象再去调用,直接用this调用。
- 对象中的一个成员调用另一个成员时可以省略this(主调必不可少,省略时默认静态主调为该类,非静态为this)
- static修饰的方法中不能使用this(类成员不能访问实例成员)类初始时对象还不存在,所以用this会出错
- 去访问因重名而覆盖的变量,可以用this前缀
- this可以作方法的返回值,可以用this连续调用同一个返回值为this方法。
方法
- java所有方法都必须定义在类中,不能单独存在
- 不能独立执行方法,必须用类或对象来调用
- 方法参数值传递
- 最后一个形参类型后增加...,表明该形参可以接受多个参数值,多个参数值被当成数组传入,参数只能放参数列表的最后
- 形参个数可变参数本质就是一个数组参数,只是调用时有差别
- 方法重载要求 同一个类 方法名相同 参数列表不用,与返回值类型修饰符等无关
- 重载可变参数个数参数的方法不安全,也降低可读性
成员变量和局部变量
- 类变量不属于实例,用实例.类变量访问的依然是实例对应的类的变量,修改也是。
- 如果成员变量没有显式初始化,类变量会在类初始时初始类变量,实例变量在创建对象时初始。
- 一个类的所有实例访问类变量时访问的是同一片内存区
- 局部变量出了形参外,所有都需要显式初始化,否则不能访问。
- 允许局部变量和成员变量重名,局部变量会覆盖成员变量,用this可以访问到被覆盖的成员变量
- 局部变量赋初值时系统才为其分配内存
- 栈内存不需要系统垃圾回收,随代码块运行结束而结束
- 变量使用规则
- 描述类或对象固有信息时用成员变量
- 所有实例相同,类相关,用类变量
- 实例相关用实例变量
- 保存类或实例状态信息的变量应该使用成员变量
- 某个类或多个方法共享的变量用成员变量
- 使用局部变量时尽可能缩小作用范围,能用代码块局部变量就不用方法局部变量
封装
- 将对象状态信息隐藏在对象内部,不允许外部程序直接访问对象内部信息,而是通过该类所提供的方法来实现对内部信息的操作和访问
- 目的
- 隐藏类的实现细节
- 让使用者只通过事先预订的方法来访问数据,从而可以在方法加入逻辑,限制成员变量的不合理访问
- 便于修改,提高代码维护性
- 实现
- 将对象的成员变量和实现细节隐藏起来,不允许外部直接访问
- 把方法暴露出来,让方法控制这些成员变量的进行安全的访问和操作
访问控制符
- 控制访问符用于控制一个类的成员是否能被其他类访问
- private 当前类内部访问
- default 同一个包中访问
- protected 同一包中的其他类和其他包中的所在类的子类访问,通常修饰方法是希望子类重写方法
- public 被所有类访问
- 局部变量不能使用访问控制符,因为一定不能被其他类访问
- 外部类只能用public和default,因为没有类内部和所在类的子类两个范围
- 实例变量的setter和getter方法,setAbc() getAbc(),在setter方法加自己的控制逻辑
- JavaBean,每个实例变量都用private修饰,每个实例变量都有public修饰的setter getter方法,JavaBean总是一个封装良好的类
- 访问控制符原则
- 绝大部分成员变量都应该使用private修饰
- static修饰,类似全局变量的考虑用public修饰
- 工具方法(辅助实现该类的其他方法)用private修饰
- 主要用作父类的类中希望被子类重写的方法,而不想被外界调用的,用protected修饰
- 类构造器、自由调用的方法用public
- 大部分外部类用public
- javac命令 -d选项为源文件生成相应文件结构
- package语句指定所在包,一个源文件只能指定一个包,只能包含一条package语句
- 同一包下的类可以自由访问,不需要添加前缀
- 不同包下刚问需要类的全名(父包名.子包名.类名)
- import导入后可省略包名 import package导入后可省略类名
- java默认为所有源文件导入java.lang包下所有类
构造器
- 构造器重载,参数列表必须不同
- 构造器不能直接互相调用,可以用this(参数……);调用别的构造器,this调用必须作为构造器执行体的第一条语句
继承
- 类的继承为单继承,extends,每个类最多只有一个直接父类
- Object是所有类的父类,要么是直接父类,要么是间接父类,所有对象都可以调用Object类定义的实例方法
- 重写父类方法,方法名相同,形参列表相同,静态非静态相同,子类返回值类型≤父类返回值类型,子类抛出的异常类≤父类抛出的异常类,子访问权限≥父访问权限
- super或父类类名作为调用者来调用父类中被覆盖的方法,如果没有同名,super或父类类名可以省略
- 父类private修饰的方法无法被子类重写,子类方法名形参相同的方法只是新定义的
- super同this,不能出现在static修饰的方法中
- 创建子类对象时同时也会为父类实例变量分配内存
- 子类的引用变量可以强制转换成父类类型的引用变量
- 子类不会获得父类构造器,但子类构造器可以调用父类构造器,super(参数...);,同样需要出现在第一行
- 系统会上溯执行最顶端的父类构造器,再依次向下执行子类构造器,所以最先总是执行java.lang.Object类的构造器
多态
- 引用变量有两个类型:编译时类型和运行时类型,两种类型不一致时出现多态
- java允许把一个子类对象直接赋给一个父类引用变量,无须任何类型转换,称为向上转型,由系统自动完成,引用变量在编译阶段只能调用其编译时类型所具有的方法,但运行时则执行运行时类型所具有的方法
- 对象的实例变量不具备多态性,访问的是编译时类型的变量
- 引用类型之间的强制类型转换只能存在于有继承关系的两个变量间且实际类型必须是需要转换的类型
- 强制转换前用instanceof运算符判断前面的对象是否是后面的类或子类或实现类的实例,返回true或false
- instanceof前面操作数的编译时类型要么与后面类相同,要么是继承关系,否则编译错误
继承与组合
- 继承会破坏封装,组合可以在实现类复用同时提供良好的封装
- 尽量不要在父类构造器中调用将被子类重写的方法,可能会出现空指针异常
- 最终类可以通过final修饰类或者private修饰构造器(可另外提供静态方法用于创建该类实例)实现
- 使用继承:子类需要额外实现 子类需要新方法或重写父类方法,其他出于复用目的的都可以用组合实现
- 实现
- 在新类里用private修饰被组合的旧类对象,在构造器中使引用变量指向旧类对象。
- 显式创建旧类对象,调用构造器传入旧类对象。
- 继承表示is a,组合表示has a
初始化块
- 同类型初始化块有先后执行顺序
- 初始化块修饰符只能是static
- 创建对象时先调用实例初始化块,再调用构造器
- 普通初始化块是假象,编译后初始化块会被还原到构造器中,且位于构造器代码的前面
- 普通初始化块和类初始化块同样会上溯
- 类初始化块不能处理实例变量,同样遵循不能访问非静态成员的规则
- 类初始化块在加载类时执行一次
- 类初始化块上溯父类后一次向下执行,后从最顶父类开始一次执行每个类的普通初始化块和构造器。(类 类 类 普 构 普 构 普 构)
- 静态初始化块和声明静态成员变量顺序按代码排列顺序
- JVM在类准备阶段就为该类所以静态成员分配内存了,初始化阶段开始执行初始化块
大概就是书上第五章的重点和细节吧,没有附上代码和例子,回忆复习时脑补,如果想不起来或者理解不了,就去翻书看对应小节。