java学习(四)
java面向对象(上)
static修饰符
static
修饰符用于修饰类的成员变量和方法,表示该变量或方法属于这个类本身而不属于任何一个实例static
修饰的方法内不能写this
,因为static
表示这个方法属于一个类,因此省略的this
引用无法指向有效的对象,静态成员不能直接访问非静态成员
当要通过类的静态方法访问非静态成员时,可以先实例化这个类,通过这个类的对象去调用该静态方法,则能够实现静态成员访问非静态成员。
java参数传递
-
java参数传递方式只有值传递,也就是形成一个副本,因此想要修改基本类型的值会失败,可以通过传递引用类型的参数加以改变;
也就是说基本类型必须包装成引用类型进行传递才能更改基本类型的值
-
形参个数可变(JDK1.5之后支持),在最后一个形参类型后加
...
再写上形参名称,表示该形参可接受多个参数值,当成数组传入 (一个方法最多一个)如:
public static void test(int a, String ... books);
-
局部变量必须初始化,因为当进入一个方法时,该方法的局部变量表所分配的内存是已经确定好的,(存储在栈内?),而根据局部变量表,所有的局部变量的内存是确定的,故创建局部变量的时候同时必须初始化它,否则编译器也会有提示。而成员变量则不必,因为成员变量的内存分配是在堆上的,JVM会在内存分配后,将这一片的内存都初始化为0。
java访问控制
private
:仅可再当前类的内部访问
default
(省略不写):包访问权限
protected
:包与子类访问权限
public
:公共访问权限
外部类仅有public
和default
访问控制符
java包
-
package语句必须作为源文件的第一条非注释性语句
-
导入包中的类:
import package.subpackage...*;
(其中*
只代表类不代表包) -
如果不导入则需要使用
package.subpackage...class
这样的全名 -
java默认导入
java.lang
包下的所有类,故使用String、System类等不需要import -
如果类重名则需要使用类的全名
-
import static
意为导入类的静态方法,因此在使用静态方法的时候可以省略类名,但要放在package
之后、类定义之前 -
常用包
java.lang
:String、Math、System、Thread等java.util
:工具类、集合框架类如Arrays、List、Set等java.net
:网络编程接口java.io
:I/Ojava.text
:java格式化java.sql
:JDBC
java继承
- 每个类最多只有一个直接父类且无法继承父类的构造函数,但可以在子类的构造函数中使用
super
调用父类的构造函数,但java实例化子类对象的时候总会从父类java.lang.Object
开始逐级向外调用构造函数这里和cpp是一样的 - 子类重写父类方法中,必须同样是static或非static
- 子类如果要使用父类被覆盖的方法或实例变量可以使用
super
(非static)或者父类类名(static)来调用 - 尽量避免在父类构造函数中调用要被子类重写的方法:父类构造函数中如果调用了被子类重写的方法则会出现预先调用子类重写的方法而带来问题。这是因为,首先子类和父类被编译成机器码,当子类实例化的时候,是按照子类的定义实例化的,但对象需要按照构造器初始化,java会首先调用父类的构造器,逐级向外初始化,如果在父类构造器中调用了将被子类重写的方法,那么根据编译时的类型是子类,这个方法其实是已经被重写的方法,如果这个方法中访问了子类定义的成员,而这个成员对于父类是未知的,就会出现运行出错。
java多态
-
复习一下多态概念:编译时的类型和运行时的类型不一致导致,编译类型由类型定义或者代码中的实例化指定的构造器决定,而运行类型则由具体的引用指向决定,取决于指向的内存类型是什么。
例如:
Parent A = new Sub()
A实例化的时候,他的引用指向了Sub类对象的内存,则运行时按照子类对象进行运行,但由于其编译类型为Parent类,故当想要访问Sub类中新定义的方法时,是无法访问的,但可以通过访问重写的方法对新定义的成员进行访问。
-
对象的实例变量不具备多态性,引用类型访问的实例变量是编译时声明的实例变量所处的类所决定的
-
java总是优先调用子类重写的方法
java强制类型转换
variatyA instanceof typeB
可用于判断变量A是否属于B类型,返回true
或false
,只要实例A的类型是类型B的父类或类型B本身就返回true
java组合
- 复习概念:组合把旧类对象作为新类成员变量组合(利用构造函数将外界已经分配了内存的对象引用进来)进来可以直接获得旧类的
public
方法,特别的在新类中以private
修饰旧类对象 - 组合和继承之间相差的内存用量只有少许引用变量带来的差别,并没有本质上的差别
java初始化块
-
初始化块之间顺序执行,修饰符只能是
static
或default
static
负责对类进行初始化,通常对类变量做初始化default
负责对对象做初始化先从顶级父类的
static
初始化块开始向子类执行(类加载时执行),之后执行顶级父类的default
初始化块之后执行构造函数再执行子类的default
初始化块、构造函数(生成对象时执行)static
初始化块和声明静态成员变量(相当于static
初始化块)时所指定的初始值顺序由代码的顺序决定。 -
创建类的对象时,系统总是先调用该类里面定义的初始化块(在构造函数之前执行)
-
default
初始化块主要用于无需接收参数的行为,可作为构造函数的补充 -
静态成员初始化分为两个阶段:默认初始化阶段:
引用变量==null,基本类型变量==0
,显式初始化阶段:所有的静态变量设置为代码中写好的初始化值,如果没有则保持默认初始化阶段得到的值。先默认初始化再显式初始化。