接触过面向对象的人都知道面向对象有三大特征,分别是封装、继承和多态。这三者分别指的是什么,为什么是这哥仨,使用他们有什么好处,我们来梳理一下。
封装
原则:隐藏对象的属性和实现细节,仅对外提供公共访问方式。
好处:
①将变化隔离。
②便于使用。
③提高重用性。
④提高安全性。
Demo1:
比如一个学生类:他具有姓名和年龄两个属性,但是为了提高安全性和重用性,便于使用,我们将其封装起来。
public class Student { private String name; private int age; public Student() { super(); //TODO Auto-generated constructor stub } public Student(String name, int age) { super(); this.name= name; this.age= age; } public String getName() { returnname; } public void setName(String name) { this.name= name; } public int getAge() { returnage; } public void setAge(int age) { this.age= age; } @Override public String toString() { return"Student [name=" + name + ", age=" + age + "]"; } }
其中,类的成员变量都用private修饰,提高安全性。
继承
概述
多个类中存在相同属性和行为时,将这些内容抽取到单独一个类中,那么多个类无需再定义这些属性和行为,只要继承那个类即可。
父类又称基类,超类;子类又称派生类。
子类可以直接访问父类中的非私有的属性和行为。
关键字为 extends
好处
提高了代码的复用性。
让类与类之间产生了关系,提供了多态的前提。
特点
a.Java只支持单继承,不支持多继承。
因为如果可以多继承,就会出现调用不明确的问题。
b.Java支持多重继承(继承体系)
什么时候用
如果多个类之间有is a 的关系时候,可以定义为继承。
定义类(A,B)的时候:
A is a B 中A是子类。
B is a A 中B是子类
注意:不要为了去继承部分功能,而去使用继承。
Demo2:
class animal { private String name; private int age; public void setName() { this.name=name; } public String getName() { returnname; } public void setAge() { this.age=age; } public int getAge() { returnage; } public void run() { System.out.println("跑步"); } public void eat() { System.out.println("吃饭"); } } class dog extends animal { publicvoid eat() { System.out.println("狗吃骨头!"); } } class car extends animal { public void eat() { System.out.println("猫吃鱼!"); } } class AnimalTest { public static void main(String[] args) { dog d = new dog(); d.eat(); d.run(); car c = new car(); c.eat(); c.run(); } }
运行结果:
狗吃骨头!
跑步
猫吃鱼!
跑步
多态
概述:在同一个方法中,由于参数不同而导致执行效果各异的现象就是多态。
拿生活中的例子来说:
水(水,冰,水蒸气)
狗:狗是狗,狗是动物,狗是宠物,狗是食物
前提条件:
A:要有继承关系。
B:要有方法重写。
C:要有父类引用指向子类对象。
多态间的成员特点:方法有重写,而变量没有
成员变量
编译看左边,运行看左边。
成员方法
编译看左边,运行看右边。
注意:多态有三种体现形式
类多态
抽象类多态
接口多态
优点:
提高代码的扩展性和可维护性。
弊端:
父类引用不能使用子类特有功能。
基本类型:隐式转换(小到大),强制转换(大到小)。
引用类型:向上转型(小到大),向下转型(大到小)。
Demo3:
class Animal { public void sing() { System.out.println("动物在唱歌!"); } } class Dog extends Animal { public void sing() { System.out.println("狗在唱歌!"); } } class Cat extends Animal { public void sing() { System.out.println("猫在唱歌!"); } public void eat() { System.out.println("猫在吃饭!"); } } public class PolyTest { public static void main(String[] args) { //向上类型转换 Cat cat = new Cat(); Animal animal = cat; animal.sing(); //向下类型转换 Animal a = new Cat(); Cat c = (Cat)a; c.sing(); c.eat(); //编译错误 //用父类引用调用父类不存在的方法 //Animal a1 = new Cat(); //a1.eat(); //编译错误 //向下类型转换时只能转向指向的对象类型 //Animal a2 = new Cat(); //Cat c2 = (Dog)a2; } }
运行结果:
猫在唱歌!
猫在唱歌!
猫在吃饭!
初看,觉不出来多态的好处,感觉和继承挺像的,这些东西不用多态照样能够实现,这是因为目前我们接触的都是小Demo,等待以后做项目的时候强调的是对修改关闭,对拓展开放。多态能在以后帮助我们达到这些目标。例如之前写过一篇文章:《谈一谈:抽象工厂+反射+配置文件实现数据访问程序》,针对一些需求的修改,我们仅仅修改一下配置文件即可,而不用对源代码动刀。当然这个例子跟接口的多态有关,所以后续笔者还会总结一下抽象类和接口类,尝试让多态的优点更多的体现出来,敬请期待!
小结
封装即隐藏对象的属性和实现细节,仅对外提供公共访问方式,保证了模块具有较好的独立性,使得程序维护修改较为容易。继承提高了代码的复用性,多态提高代码的扩展性和可维护性。三者共同达到了一个目的:使得对应用程序的修改带来的影响更加局部化,程序更加健壮,而且易维护、更新和升级。
原文地址:http://blog.csdn.net/haovip123/article/details/43889207