十一、抽象类
1、抽象类的特点:
- 抽象类和抽象方法必须用abstract关键字修饰
- 抽象类一般会有一个 public 的方法,作为访问的入口。
- 抽象方法,一般使用 protected 关键字修饰,用于子类重写。
- 内部使用的方法,为 private 修饰。
- 抽象类中不一定有抽象方法,但是有抽象方法的类必须定义为抽象类。
- 抽象类不能实例化 ,但是抽象类有构造方法,作用在于子类访问父类数据的初始化。
- 抽象的子类
- 如果不想重写抽象方法,该子类是一个抽象类。
- 重写所有的抽象方法,这个时候子类是一个具体的类。
- 抽象类的实例化其实是靠具体的子类实现的。是多态的方式。
- AbstractAnimal a = new Cat();
2、抽象类的成员特点:
1)成员变量:既可以是变量,也可以是常量。
- 构造方法:有。用于子类访问父类数据的初始化。
- 成员方法:既可以是抽象的,也可以是非抽象的。
2)抽象类的成员方法特性:
- 抽象方法: 强制要求子类做的事情。
- 非抽象方法: 子类继承的事情,提高代码复用性。
3、abstract不能和哪些关键字共存?
- private 冲突 。abstract 必被重写,private只能自己实现。
- final 冲突 。
- static 无意义 。
十二、接口
1、接口的特点
- 接口用关键字interface表示
- 类实现接口用implements表示
- 接口不能实例化 ,按照多态的方式来实例化。
- 接口的子类
- 可以是抽象类。但是意义不大。
- 可以是具体类。要重写接口中的所有抽象方法。(推荐方案)
2、接口成员特点
1)成员变量,只能是常量,并且是静态的。
- 默认修饰符:public static final
2)构造方法:接口没有构造方法,但是超类 Object有无参的构造方法。
3)成员方法:只能是抽象方法。
3、继承与实现
1) 类与类:
2)类与接口:
- 实现关系,可以单实现,也可以多实现。
- 并且还可以在继承一个类的同时实现多个接口。
3)接口与接口:
3、抽象类和接口的区别:
1)成员区别
- 抽象类:
- 成员变量:可以变量,也可以常量
- 构造方法:有
- 成员方法:可以抽象,也可以非抽象
- 接口:
2)关系区别
3)设计理念区别(《java编程思想》)
- 抽象类
- 被继承体现的是:”is a”的关系。抽象类中定义的是该继承体系的共性功能。
- 接口
- 被实现体现的是:”like a”的关系。接口中定义的是该继承体系的扩展功能。
十三、形式参数和返回值的问题深入研究
1、 形式参数:
- 基本类型:值
- 引用类型
- 类名:需要的是该类的对象
- 抽象类:需要的是该抽象的类子类对象
- 接口:需要的是该接口的实现类对象
2、 返回值:与形参一致
十四、包
1、packag 关键字
2、import 关键字
十五、权限修饰符
1、public :公开,全部可以访问
2、protected:所有子类(同包或不同包)、同包下的所有类访问
3、default:同包下所有类。
4、private:本类内部访问
十六、内部类
1、特点
- 1)定义在其他类的内部,这个类就被称为内部类。 类A中定义了一个类B,类B就是内部类
- 2)内部类可以直接访问外部类的成员,包括私有。
- 3)外部类要访问内部类的成员,必须创建对象。(且访问不同的内部类,方式不同)
2、分类:
- 成员内部类:在成员位置定义的类
- 局部内部类:在局部位置定义的类
3、 访问:
- 内部类可以直接访问外部类的成员与方法。
- 访问成员内部类的成员。
<span style="font-family:Arial;font-size:18px;">外部类名.内部类名 对象名 = 外部类对象.内部类对象;
Outer.Inner oi = new Outer().new Inner();</span>
- 在局部位置,可以创建内部类对象,通过对象调用内部类方法,来使用局部内部类功能
<span style="font-family:Arial;font-size:18px;">
InnerObject2 tInnerObject2 = new InnerObject2();
tInnerObject2.C();</span>
- 静态方法不能创建内部类实例对象 (多线程的时候,在main方法中需要起线程,会出现这个问题)
- 原因: 内部类可以访问外部类的成员变量,成员变量是在对象创建后才分配空间的,静态方法中可以不创建对象即访问对象的方法。
- 如 Outputer是内部类,可以访问外部类的成员变量,即一定有了外部类的实例对象,但是在main方法中根本不需要创建外部类对象,就矛盾了。
4、 成员内部类的修饰符:
- private 为了保证数据的安全性 。
- static 为了方便访问数据 。
- 注意:静态内部类访问的外部类数据必须用静态修饰。
- 内部类用静态修饰是因为内部类可以看出是外部类的成员
- 成员内部类被静态修饰后的访问方式是
- 外部类名.内部类名 对象名 = new 外部类名.内部类名();
- 外部类名.内部类名.方法名()
- static 不能修饰外部类,但是可以修饰内部类。
5、成员内部类面试题
- 内部类和外部类没有继承关系。
- 变量的就近原则。
- this 的限定当前对象的功能。
- 通过外部类名限定this对象 :Outer.this
6、 局部内部类
1)面试题: 局部内部类访问的局部变量必须用 final 修饰 。(动态代理会有涉及)
- 局部变量是随着方法的调用而在栈中调用,随着调用完毕而消失。而new出来的局部内部类,在堆内存的内容并不会立即消失。
- 这时就出现一个现象,局部内部类需要访问局部变量,而局部变量已经消失。
- 所以,我们给局部变量加 final 修饰,加入final修饰后,这个变量就成了常量。(可以使用javac查看class文件)
- 既然是常量,你消失了,我在内存中存储的是数据的值,所以,我还是有数据在使用。
7、匿名内部类
1) 匿名内部类 :就是内部类的简化写法。
2)前提:存在一个类或者接口 。这里的类可以是具体类也可以是抽象类。
3)格式:
<span style="font-family:Arial;font-size:18px;"> new 类名或者接口名(){
4)本质是什么呢? 是一个继承了该类或者实现了该接口的子类匿名对象。
8、匿名内部类的使用
<span style="font-family:Arial;font-size:18px;">
System.out.println("好好学习,天天向上");
9、匿名内部类的面试
<span style="font-family:Arial;font-size:18px;">匿名内部类面试题:
interface Inter { void show(); }
public static void main(String[] args) {
要求在控制台输出”HelloWorld”</span>
1)Outer.method()可以看出method()应该是Outer中的一个静态方法。
2)Outer.method().show()可以看出method()方法的返回值是一个对象。
又由于接口Inter中有一个show()方法,所以我认为method()方法的返回值类型是一个接口。
<span style="font-family:Arial;font-size:18px;">class Outer {
public static Inter method() {
System.out.println("HelloWorld");
十七、面向对象的特征
(一)封装
1、利用 private 属性修饰成员变量。使得在类体外无法通过对象直接访问成员变量。
2、创建成员变量的setXxx() 和 getXxx() 方法,访问set| get方法来访问成员变量。
(二)继承
1、Java的单继承,利用接口实现多继承。
2、子类可以重写父类的方法,也可以不重写。
3、super关键字,用于子类的构造函数中,调用父类的构造函数。
(三)多态
1、前提
2、对象转型:
- 向上转型:F f = new Z();
- 向下转型:Z z = (Z)f;
3、以后开发,使用接口处理。如
- XXXDao 和 XXXDaoImpl。
- 如注入的时候,可以使用接口处理。
4、多态的实现方式
- 具体类多态(几乎没有)
- 抽象类多态(常用)
- 接口多态(最常用)