一、面向对象三大特性
继承、封装、多态
1 继承性
目的:减少代码的重复,提高程序可维护性
方法:将代码相同的部分提取出来组成一个父类
类之间的继承关系是现实世界中遗传关系的直接模拟,它表示类之间的内在联系以及对属性和操作的共享,即子类可以沿用父类(被继承类)的某些特征。子类也可以具有自己独立的属性和操作。
子类从父类继承有两个主要的方面:
属性的继承
方法的继承
类定义的格式:
[ 类修饰符] class 类名 [ extends 父类名 ][ implements 接口名 ]
{
成员变量定义;
方法定义;
}
注意:
Java是单继承,一个子类只能有一个父类,但一个父类可以拥有多个子类。
构造方法的继承
1.子类可以无条件继承父类不含参数的构造方法。
2.如果子类有构造方法,那么在创建子类对象时,则将先执行继承下来的父类的构造方法,然后再执行自己的构造方法
3.对于父类中包含有参数的构造方法,子类可以通过在自己的构造方法中使用super关键字来引用,而且必须是子类构造方法中的第一条语句。
继承的顺序
先父类先static先变量再方法
this 和 super关键字
this指向调用该方法的对象(1构造器中引用该构造器正在初始化的对象2在方法中引用该方法调用的对象)
super指向由父类生成的对象
区别:
引用父类方法时,为了明确需要加上super
子类当前方法中形参与成员变量或局部变量相同时,采用this
2 封装
目的:将对象的使用者和设计者分开
类比:汽车的左转、右转(方向盘 与 车轮); 被陶瓷封装的集成芯片
在类的定义中设置对对象中的成员变量和方法进行访问的权限。
提供一个统一供其它类引用的方法。
其它对象不能直接修改本对象所拥有的属性和方法。
访问控制符
Public
一个类作为整体对程序的其他部分可见,并不能代表类内的所有属性和方法也同时对程序的其他部分可见,前者只是后者的必要条件,类的属性和方法能否为所有其他类所访问,还要看这些属性和方法自己的访问控制符
默认访问(包访问特性)
默认的访问控制权规定类或者类成员只能被同一个包中的其他代码所访问,在包外不可见。这种访问特性称为包访问性。
Package创建了新的命名空间 Import关键字用于导入包
Private
私有只能被该类中的其他变量访问,在该类外不可用。
Protected
对于同一个包中的类可见,且对于该包中该类的子类可见。
3 多态性
由于父类和子类可以有同名的方法,
在运行时JVM根据方法的调用对象的不同或者参数个数和类型的不同来查找、决定执行哪个版本的方法,称为多态性
多态的特点是采用同名的方式,根据调用方法时调用对象的不同、传送的参数的多少以及传送参数类型的不同,调用不同的方法
多态性分为:
编译时多态(重载Overload)
运行时多态(重写Overwrite/覆盖Override)
覆盖:子类继承了父类的同名无参函数。当子类从父类继承了一个无参函数,而又定义了一个同样的无参函数,则子类定义的方法覆盖父类的方法,称为覆盖。
重载:子类继承了父类的同名有参函数。当子类继承了父类的一个同名方法,且方法参数不同,称为重载。通过方法的重载,子类可以重新实现父类的某些方法,使其具有自己的特征。
重写:当前类的同名方法。通过方法的重写,一个类可以有多个具有相同名字的方法,由传递给它们不同的个数和类型的参数来决定使用哪种方法。因此,重写的名称是当前类中的同名函数,不是父类中的函数名。
实现运行时多态的条件:
1 继承
2 重写(覆盖)
3 父类引用指向子类对象
final关键字
final 修饰的变量为最终成员变量
final 修饰的方法为最终方法
最终成员变量一般是在声明时进行初始化,一旦最终成员变量被赋值,则它在整个程序执行过程中不能改变。
当声明常量时,可以使用final 加上类型和常量名
最终方法不能被重复定义或更改方法的内容,不能被覆盖
比较方法
==
基本数据类型即 比较数值
若比较引用类型变量,需要该两个变量引用同一个对象时才返回true
Object.equals
引用对象与当前对象相同,才返回true
Integer int1=new Integer(1);
Integer int2=new Integer(1);
String str1=new String("Hello");
String str2=new String("Hello");
System.out.println(int1==int2); //打印false
System.out.println(int1.equals(int2)); //打印true
System.out.println(str1==str2); //打印false
System.out.println(str1.equals(str2)); //打印true
抽象类abstract
抽象类通常都包括一个或多个抽象方法(只有方法说明,没有方法体)
抽象方法体中内容,根据继承抽象类的子类的实际情况,有子类完成其抽象方法的代码。
抽象类 里 可以有 非抽象的方法。
抽象类 里 可以没有 抽象方法。
即使没有抽象方法的抽象类也不允许实例化。
一个类里有abstract方法的话,该类必须为abstract。
抽象方法一定不能有方法体(哪怕是空方法体)。
接口 interface
[访问控制符] interface 接口名 {
抽象方法声明
成员变量声明
}
实际上可以把接口理解成为一种特殊的抽象类。
接口不能被实例化。
和类的访问级别类似,接口的访问控制符是 public 或者默认访问。
如果接口本身定义成public,所有抽象方法和成员变量都是public的,不论是否使用了public访问修饰符
接口中的所有方法都是抽象方法,在接口中只能给出这些抽象方法的方法名、返回值类型和参数列表,没有方法体。(类似C++的“纯虚类”)
接口中可以有成员变量(但变量不能用private和protected修饰)
接口中的变量,本质上都是static,而且是final的 ,无论是否用static修饰,必须以常量值初始化
实际开发中,常在接口中定义常用的变量,作为全局变量使用
访问形式: 接口名.变量名
一个接口不能继承其它的类,但是可以继承别的接口
一个类可以实现多个接口
抽象类与接口的区别
1.语法定义的角度
2.从编程的角度
抽象类是继承的体现,一个类只能继承自一个类,却可以有多个接口。
抽象类定义中可以有方法的默认行为(return0.0)
接口却不能有默认行为
接口的实现只需要相关函数定义即可,即使没有任何实现。
3.从设计的角度
接口表示类遵从接口的协议,即不会发生大的改动。
工厂模式
简单工厂模式属于类的创建型模式,又叫做静态工厂方法模式。通过专门定义一个类来负责创建其他类的实例,被创建的实例通常都具有共同的父类。
(简单说,即专门设计一个类作为父类与其他类交互的类)
1. 抽象(Product)角色简单工厂模式所创建的所有对象的父类,它负责描述所有实例所共有的公共接口。
2. 具体产品(Concrete Product)角色简单工厂模式所创建的具体实例对象
3. 工厂(Creator)角色简单工厂模式的核心,它负责实现创建所有实例的内部逻辑。工厂类可以被外界直接调用,创建所需的产品对象。
优点:
在这个模式中,工厂类是整个模式的关键所在。
它包含必要的判断逻辑,能够根据外界给定的信息,决定究竟应该创建哪个具体类的对象。用户在使用时可以直接根据工厂类去创建所需的实例,无需了解对象是如何创建以及如何组织的。
有利于整个软件体系结构的优化。
缺点:
简单工厂模式的缺点也正体现在其工厂类。
工厂类集中了所有实例的创建逻辑,“高内聚”方面不佳。
另外,当系统中的具体产品类不断增多时,可能会出现要求工厂类也要做相应的修改,扩展性并不很好。