写在最前
前言
复用代码是Java众多引人注目的功能之一,我们来看看它是怎么实现的,并且能做些什么?
(1)使用组合实现复用
- 什么是组合?
组合的意思就是,在一个新创建的类中创建已有的对象,并使用这个对象。
用书上的代码举个例子:
在SpringklerSystem 类中new了一个WaterSource 的对象,并使用到了WaterSource 类中的toString()方法。
class WaterSource {
private String s;
WaterSource() {
System.out.println("WaterSource()");
s = "Constructed";
}
public String toString() {
return s;
}
}
public class SpringklerSystem {
private String value1, value2, value3, value4;
private WaterSource source = new WaterSource(); // 在这里体现的组合
private int i;
private float f;
public String toString() {
return "value1 = " + value1 + " " +
"value2 = " + value2 + " " +
"value3 = " + value3 + " " +
"value4 = " + value4 + "\n" +
"i = " + i + " " + "f = " + f + " " +
"source = " + source;
}
public static void main(String[] args) {
SpringklerSystem springklerSystem = new SpringklerSystem();
System.out.println(springklerSystem);
}
}
(2)使用继承实现复用
- 使用继承后,导出类和基类的关系就特殊起来了:“导出类是一种基类”
- 导出类会获得基类的所有域和方法(获得了…用不用的了是另一回事…像是private修饰的域和方法)
- 举个Son继承Father,从而复用Father的代码的例子:
class Father {
private String name;
Father(String name) {
this.name = name;
}
public void introduce() {
System.out.println("我是:" + name);
}
}
class Son extends Father{
Son(String name) {
super(name);
}
}
class Solution{
public static void main(String[] args) {
Father son = new Son("wangz7");
Father father = new Father("baba");
son.introduce();
father.introduce();
}
}
--------------------------------------------------------------------
输出:
我是:wangz7
我是:baba
(3)使用代理实现复用
- 代理的方式,是一种类似继承和组合折中的方式,它解决了:继承之后,导出类会将父类的所有方法暴露出来这个问题。
- 也就是用组合的思路,在类中new 出来需要复用的对象,并且按照这个对象中需要复用的部分,用自己的方法对它的方法进行包装,并可以增加自己的细节。
class Human {
private String name;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
class Proxy {
Human human = new Human();
public void setHumanNameByProxy(String name) {
human.setName(name + "---by proxy"); 使基类的方法不暴露的同时,对基类的方法进行了增强
}
public String getHumanNameByProxy() {
return human.getName();
}
}
class Solution {
public static void main(String[] args) {
Proxy proxy = new Proxy();
proxy.setHumanNameByProxy("wang");
System.out.println(proxy.getHumanNameByProxy());
}
}
在组合和继承之间区别?
- 组合和继承其实都是将对象置于新的类中,组合是显式的,继承是隐式的。
- 组合一般用于:想在一个新的类中使用原有类的功能,但是想让用户使用新类的时候,看到的是只有新类,而看不嵌入的对象。(这种通常可以用private声明嵌入的对象)(新类 has a 嵌入类)
- 继承一般用于,已有一个一般类,而在它的基础上想要开发一个特殊的导出类,属于is-a的关系(导出类 is a 基类)
组合和继承究竟如何选择?
- 其实通过继承的方式进行代码复用真的不常用…应当慎用继承!
- 一个最清晰的判断思路就是:看看是否有需要,用到向上转型,如果向上转型必须用到,那么毫无疑问的选择继承!
- 关于向上转型的理解在这
【end】