继承是实现类重用的重要手段,但继承带来了一个最大的坏处,破坏封装。相比之下,组合也是实现类重用的重要方式,而采用组合方式来实现类重用则能提供更好的封装。
为了保证父类的封装性,设计父类时应当注意的问题:1尽量隐藏父类的内部数据。尽量把父类的所有field都设置成private访问类型,不要让子类型直接访问父类的field
2.不要让子类随意可以访问,修改父类的方法。如果不想被子类访问,就将父类的方法改成用private修饰,如果不想被子类方法复写,就将父类方法改成用final修饰,如果父类的某个方法希望被子类访问,而不希望被其它类访问,则用protected修饰。
3.尽量不要在父类构造器中调用将要被子类重写的方法。
那到底什么时候采用继承呢?
1.子类需要额外增加属性,而不仅仅是属性的改变。例如从person类派生出student类,person类里没有提供grade属性,而 student类需要grade属性来保存student对象就读的年级,这种父类到子类的派生,符合继承的前提
2.子类需要增加自己独有的行为方式(包括新增的方法或重写父类的方法)。例如从person类派生出teacher类,其中teacher类需要增加一个teaching方法,该方法用于描述teacher对象独有的行为方式:教学。
利用组合实现复用
class Animal
{
private void beat()
{
System.out.println("xinzangtiaodong");
}
public void breath()
{
beat();
System.out.println("xiqi");
}
}
class Bird extends Animal
{
public void fly()
{
System.out.println("feixaing");
}
}
class Wolf extends Animal
{
public void run()
{
System.out.println("wonengpao");
}
}
public class InheritTest
{
public static void main(String[] args)
{
Bird b=new Bird();
b.breath();
b.fly();
Wolf w=new Wolf();
w.breath();
w.run();
}
}
//利用组合实现复用
class Animal
{
private void beat()
{
System.out.println("xinzangtiaodong");
}
public void breath()
{
beat();
System.out.println("xiqi");
}
}
class Bird
{
private Animal a;
public Bird(Animal a)
{
this.a=a;
}
public void breath()
{
a.breath();
}
public void fly()
{
System.out.println("wohuiffei");
}
}
class Wolf
{
private Animal a;
public Wolf(Animal a)
{
this.a=a;
}
public void breath()
{
a.breath();
}
public void run()
{
System.out.println("paopao");
}
}
public class CompositeTest
{
public static void main(String[] args)
{
Animal a1=new Animal();
Bird b=new Bird(a1);
b.breath();
b.fly();
Animal a2=new Animal();
Wolf w=new Wolf(a2);
w.breath();
w.run();
}
}