面向过程:强调的是功能行为,以函数为最小单位,考虑怎么做。
面向对象:将功能封装进对象,强调具备了功能的对象,以类/对象为最小单位,考虑谁来做。
区别:
- 面向过程性能比面向对象高,因为类的调用需要初始化实例,开销较大;
维护难、复用难面向对象具有封装、继承、多态的特性,可设计出低耦合的系统,使得系统更加灵活,便于维护;性能比面向过程低较低
联系 :面向对象的底层是面向过程,将面向过程抽象成类,然后进行封装
封装把一个对象的属性私有化,同时提供一些可以被外界访问的属性的方法
相当于造了个“黑盒子”,盒子上有一些按钮可以改变盒子的相关特性,但是盒子内部构造如何,我们并不知道。
一般的,将类的属性定义为private类型,只允许类内自己访问,对外隐藏,外部要想访问,只能通过对外开放的公开的get()和set()方法
//定义私有属性
private String name;
private int age;
private boolean sex;
alt+Insert 快速生成对象属性的set()、get()方法
public String getName() {
return name;
}
public int getAge() {
return age;
}
public boolean isSex() {
return sex;
}
public void setName(String name) {
this.name = name;
}
public void setAge(int age) {
this.age = age;
}
public void setSex(boolean sex) {
this.sex = sex;
}
注:访问隐藏属性的方法必须声明为public的,否则属性无法访问
继承Java中单继承多实现,即只能继承一个类,可以实现多个接口
继承是使用已存在的类的定义作为基础建立新类的技术,新类的定义可以增加新的数据或新的功能,也可以用父类的功能,但不能选择性地继承父类。通过使用继承我们能够非常方便地复用以前的代码。
关键字:extends
特点:
1.子类拥有父类非 private 的属性和方法。
2.子类可以拥有自己属性和方法,即子类可以对父类进行扩展。
3.子类可以用自己的方式实现父类的方法(重写)。
举个栗子,
//定义父类
class Father{
//无参构造器
// 如果只是定义有参构造器,子类的构造器应该在第一行使用super关键字得到父类的相应属性
public Father() {
}
public Father(String name) {
this.name = name;
}
private String name;
public int age;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public void punish(){
System.out.println("The father will educate his next generation !!!");
}
}
//使用继承的方式构建子类
class Son extends Father{
}
子类继承父类所有的非私有属性和方法,不能选择性地继承
为子类添加新的方法
class Son extends Father {
public void educated() {
System.out.println("The son has been punished by his father !");
}
}
可以看到,子类可以调用其特有的方法educated()
一个引用变量到底会指向哪个类的实例对象,该引用变量发出的方法调用到底是哪个类中实现的方法,必须在程序运行期间才能决定。
多态分类:
编译时多态:相同的方法名因为参数不同产生了多种状态,需要依赖传入的参数来确定到底调用哪一个方法,也就是说,程序编译期间就已经能够确定下来要调用哪个方法,方法的重载就是编译时的多态
运行时多态(我们平时所说的多态):父类的引用指向的子类需要在程序运行时确定
重载和重写:
重载:同一个类中、方法名相同、返回值相同、参数列表不同(参数个数、顺序、类型等,有一项不同就可以定义为参数列表不同)------“三同一不同”
重写:就是覆盖,在继承关系中,子类对父类的同名同参方法进行自己的实现,且范围不能大于父类
1. 继承关系
2. 子类要重写父类的方法
3. 父类的引用指向子类(向上转型)
需要将子类的引用赋给父类对象,只有这样该引用才能够具备技能调用父类的方法和子类的方法相当于把子类对象转为父类对象,减弱了各个子类对象之间的差异(消除了子类对象特有的方法),保留下来父类中已有的方法(必须被重写,否则大家实现的功能都一样,就不能称之为多态),写出更加通用的代码,以适应不同的需求要实现相应的子类的功能(父类中不曾定义的),将父类对象的引用赋给子类对象,就可以实现子类中的对应功能
//定义两个子类,均重写了父类的方法punish(),而且都有其特有的方法
class Son1 extends Father {
public void haha() {
System.out.println("The son1 has been punished by his father !");
}
@Override
public void punish() {
System.out.println("Punished by father ");
}
}
class Son2 extends Father {
public void study() {
System.out.println("The son2 has been admired by his father !");
}
@Override
public void punish() {
System.out.println("Punished by bad grades ");
}
}
向上转型后,各子类独有的方法就访问不到了,只能调用父类中已经定义的方法
需要调用子类特有的方法时,将父类对象向下转型,就可以实现
- 访问成员变量,编译看父类,运行看父类访问方法,编译看父类,运行看子类
能够访问的方法必须是父类中已有的方法,子类的方法由于向上转型的原因,无法访问
在运行时,由于不同的子类对该方法重写的方式不同,在程序运行过程中,看是要运行哪个子类重写的方法访问静态方法,编译和运行都看父类
静态方法在类加载的时候产生,内存中只有一份,也叫类方法,类的所有对象实例共享一份类方法,所以编译运行都看父类



