JAVA面对对象
Unit 01 对象和类
2019/5/13 12:34:21
一、从面对过程到面向对象
- 面向过程的弊端:缺乏对数据的封装;数据和方法(对数据的操作)的分离。
- 面对对象:以对象为核心,围绕对象操作。
二、类
- 类是一种数据类型。
- 类里面定义了抽象数据(成员变量),还定义了可以对该类型实施的操作(方法)。
- 创建一个类的语法
[修饰词] class 类名 { 多个成员变量 多个方法 }
- 修饰词:public、final、abstract等,不加就是默认类型。
- 成员变量:
[修饰词] 方法返回值类型 成员变量名
。创建对象后,如果不对其成员变量赋值系统就会默认初始化。 - 方法: `[修饰词] 方法返回值类型 方法名(参数列表){方法执行体}
成员变量的类型 | 默认初始值 |
---|---|
数值类型 | 0 |
boolean型 | false |
char | /u000 |
引用类型 | null |
三、对象、引用和指针
- 使用new来创建对象
Person p = new Person();//产生了两个东西:Person类型的p变量与Person对象
- p是栈内存的一个引用类型变量指向了堆内存中的Person对象。
- 访问对象的成员变量以及方法
Cell c = new Cell();
c.row = 3;//访问成员变量
c.drop();//调用方法
Unit 02 方法、引用类型数组
一、方法的重载
- 方法的签名:“方法名+参数列表” 叫方法的签名。java不允许相同的方法签名但是允许相同的方法名。
- 重载:我我们把方法名相同但是参数列表不同的这种形式叫做方法的重载(overload)。程序编译时会根据签名来绑定调用方法。
二、构造方法
- 作用:是一种,方法名要和类名相同,且没有返回值类型(void都没有),作用是对成员变量赋值。如果自己不写构造方法的话java会默认给一个无参的默认构造方法,这个方法会对成员变量赋默认值。
- 构造方法可以重载。
- 创建对象时程序会自动调用构造方法。
- this关键字
- 用来指向调用当前方法的对象,哪个对象调用的方法,this就指向哪个对象。
- this可以省略,但是当初始化的成员变量的参数和成员变量名相同时就不可省略了。
public Cell(int row, int col){
this.row = row;
this.col = col;
三、引用类型数组
Cell [] cs = new Cell[]; //数组属于引用数据类型
Cell[] cs = Cell[4];//cs是Cell数组类型,给其赋予长度4
Cell[0] = new Cell();//为每一个元素都指向具体对象,否则默认初始值为null,这时候是没意义的。
- 二维数组
int [][] arr = new int[3][]
arr[0] = new int[3];
arr[1] = new int[4];
arr[2] = new int[3];
Unit 03 对象内存管理、继承的意义(上)
2019/5/13 13:53:57
一、内存管理
- class文件在JVM上运行,JVM提供程序运行的内存空间。JVM内存分为堆、栈、方法区 三个区域。
- 堆内存
- 存储使用new关键字的对象。
- 生命周期:堆内存中的对象一旦没有引用类型变量指向,就会被java的垃圾回收机制给回收。所以对没用的对象可以对其赋值null。
内存泄漏:不再使用的内存没有被及时回收。
- system.gc()方法用于建议虚拟机马上调度GC线程回收资源,具体实现策略还要取决于不同的JVM系统
- 非堆-----栈
- 存储方法中声明的局部变量
- 生命周期:一个程序运行时调用了一个方法,那么系统就会为这个方法在栈中开辟一个叫做“栈帧”的空间,里面存了方法的参数、局部变量等数据。当这个方法完成调用后,栈帧就会被清除,里面的数据也随之消失。
- 局部变量与成员变量的区别:
1)成员变量定义在方法外;有默认值;所有类被实例化后,被存放在堆中。
2)局部变量定义在方法内;没有默认值;方法调用时存在栈帧中。
- 非堆—方法区
方法区用于存储类的信息,方法只有一份,多个对象在堆中有各自的空间,通过this区分是哪个对象调用的方法区的方法。
二、继承
- extends关键字
- 类的继承通过extends实现
- 子类可以调用父类的成员变量和方法,自己用时也可以单独定义成员变量和方法。
- 一个类只能继承一个父类,但是一个父类可被多个类继承。
- 继承拥有传递性
- 继承中的构造方法
子类构造方法必须通过super关键字调用父类的构造方法。没有写super调用的话系统会默认给一个无参的父类构造方法,但是如果父类没有无参的构造方法的话就会报错。 - 父类引用指向子类对象
- 向上造型:父类型引用指向子类型
Tetromino t = new T(5,3);
- 通过父类的引用只能访问父类所定义的成员,不能访问子类拓展的部分。
new能点出来什么看的是引用类型而不是对象。
Unit 04 继承的意义(下)、访问控制、static与final
一、重写
- 两个类关系为继承关系,方法签名相同的方法叫方法的重写。
- 调用哪个方法要看new的对象,new的谁调用的就是谁的方法。
- 子类重写父类的方法,可以用super关键字调用父类的重写方法。
- 重写与重载的区别:
- 重载:在一个类中定义,签名不同。编译过程只看语法对错,内存还不会分配。
- 重写:父子类中定义,签名相同。
二、包的概念
- 包用来解决类名重复的问题。java建议每个类前面都写包名。
- 包支持多层嵌套。
- import关键字用来声明外包的类、引入外包的类的。
import 包名.包名.类名;
三、访问控制修饰符
- 封装的意义:封装一些容易变化的、具体的实现细节,外界不可访问。这样可以降低代码出错概率,便于维护。
- private、public
- private修饰的成员变量和方法只能在本类中调用
- public修饰的成员变量和方法可以再任何地方调用。
- protect与默认访问控制
- protected修饰成员变量以及方法时可以被本类、子类、同包类使用。
- 默认访问控制(就是前面什么都不加)修饰的成员变量以及方法可以被同一个包中的类以及本类使用。
四、static、final
- static
- 修饰成员变量:static修饰的成员变量属于类而不属于对象,staic修饰的成员变量和类一起存储在方法区中,而不是在堆中,且一个类的static成员变量只有一份,如果被不同对象调用,他们调用的也是同一个变量。
调用时用“类名.静态变量(就是static修饰的)”或者“对象.静态变量”都可以。 - static修饰方法
静态方法没有隐式的this,只能直接访问静态变量。静态方法只和参数有关,和实例变量(非static修饰的成员变量)无关。static方法调用时没有具体的对象,因此static方法中不能对非static成员进行访问。 - static块
属于类的代码块,在类加载期间执行的代码块,只执行一次,可以用在软件中加载静态资源(图片、视频、音频等)。
- final关键字
- 修饰变量
- final修饰成员变量时次变量就不可改变了。
- final修饰成员变量只能在两种情况下使用:
- 声明同时初始化。
- 构造方法中初始化。
- final也可以修饰局部变量,但是需要先初始化。
- 修饰方法
- final修饰的方法不可以被重写。
- 修饰类
- final修饰的类不能被继承,但是可以继承别的类。
- staic final常量
- 必须声明同时初始化。
- 编译时会被常量替代。
Unit 05 抽象类、接口和内部类
抽象类
-
抽象方法:由abstract修饰,没有方法体的方法。
abstract void drop();
-
抽象类:由abstract修饰的类。
-
包含抽象方法的类必须是抽象类,但是抽象类不必一定包含抽象方法。
-
抽象类不能被实例化(就是不能创建对象)
-
抽象类被继承时,子类有两种方法继承。
- 子类也声明为抽象类
- 子类重写父类中的抽象方法。
- abstract、final不可以同时修饰类。
- 抽象类的意义:
- 封装子类的公共成员;为子类提供一个公共的类型。
- 定义抽象方法:由子类做不同的实现,但入口(方法名)是一样的。
接口
- 接口就是一个标准、一个规范,只要遵守了这个规范,就能干某些事。
- 接口中只能包含常量和抽象方法,接口里面变量默认就是常量,默认publlic static final;方法也是默认public abstract(不能有普通方法)。
- 接口(interface)不能被实例化;可以被其子类(实现类implements)实现,但是子类要把接口中的所有的抽象方法都实现。
- 一个类可以去实现多个接口。
- 重写:
- 方法名相同,参数列表相同。
- 子类的修饰访问权限要大于等于父类(因为接口的方法、常量默认都是public的,所以其实现类里面的方法都要加public前缀)。
- 类又继承父类又实现接口,需先继承后实现。
- 接口与接口之间可以继承。
- 接口和抽象类的区别:
Unit 06 多态、接口和内部类
多态
- 多态的意义:
- 一个类型的引用在指向不同的对象时会有不同的功能。
- 同一个对象造型成不同类型时具有不同的行为。
- 向上造型:
一个对象可以向上造型的类型有:
- 父类类型
- 实现了对应接口的类型
- 强制转型:
从小类型到大类型是不需要强转的,例如子类转为父类。只有从大类型到小类型需要强转。但是对大类型转为小类型就需要一些条件才能强转。- 父类型转为子类型:new的对象要是其子类才行。
- 转为接口时:new的对象要实现了接口的所有方法。
- instanceof关键字
通过instanceof关键字可以判断是否可以强转。
内部类
- 定义:一个类只能被另一个类使用,对外是不可见的,这个类写在外部类的里面,只能被外部类使用。
- 内部类的对象通常只在外部类中创建,内部类中可以直接访问外部类的所有成员。(Inner对象会有一个隐式的引用指向创建它的Outer类对象)。
- 匿名内部类
- 何时使用:一个类(只能是子类或者实现类),它只需创建一个对象,创建完成之后就不用这个类的时候。
- 怎么创建:main方法中:
Inter o = new Inter(){};
- 语法:
SuperType obj = new Supertype(){---};//Supertype代表匿名类的父类或者所实现的接口。最后别忘了在花括号后面加“;”。