裝飾模式Decorator(包裝器Wrapper):app
目的:對對象的相應功能進行加強。
應用:對提供基礎功能的類進行個性化加強。
兩大要素:
1,被裝飾的類封裝於裝飾實現類的內部,從而造成對象之間的引用關係。
2,裝飾實現類一樣實現了原始接口(原始接口即:被裝飾類實現的接口)
說明:
對象可能被裝飾屢次,最後的效果就是對象被包裝了多層,故裝飾器也包裝器Wrapper。
eg:
DecoratorBase繼承且封裝了targetObj對象,
DecoratorOne繼承(或封裝了)DecoratorBase對象,
DecoratorOneForA繼承(或封裝了)DecoratorOne對象,
即:targetObj對象從裏到外被DecoratorBase、DecoratorOne、DecoratorOneForA包裝了3層。
裝飾模式與繼承相比的優勢:
裝飾類不依賴被裝飾的類。緣由:在裝飾類內部封裝的是原始接口,而並非被裝飾的類!this
利用裝飾模式裝飾原有的類(即被裝飾的類)的功能:
1,編寫一個類,並實現原始接口(原始接口即:被裝飾的類實現的接口)
2,在類中定義一個原始接口類型的成員變量,用於封裝被裝飾的類的實例。
3,在類中定義構造方法,傳入被裝飾類的實例。
4,對於要裝飾的方法,改寫便可
5,對於不須要裝飾的方法,調用原有的對象的對應方法
jdk中的裝飾模式:
/**
* 裝飾器FilterInputStream,能夠包裝InputStream的任何一個子類。
* 裝飾器FilterInputStream封裝了被裝飾的對象in,且包裝器實現了被裝飾對象的接口。
*/
public class FilterInputStream extends InputStream {對象
// 被裝飾的對象
protected volatile InputStream in;繼承
/**
* 將被裝飾的對象傳入進來,這裏被裝飾的對象能夠是InputStream的任何一個子類。
* 換句話說就是,InputStream的任何一個子類均可以被BufferedInputStream包裝。
*/
protected FilterInputStream(InputStream in) {
this.in = in;
}接口
public int read() throws IOException {
return in.read();
}
}get
/**
* 裝飾器BufferedInputStream,能夠包裝InputStream的任何一個子類。
* 裝飾器BufferedInputStream封裝了被裝飾的對象in,且包裝器實現了被裝飾對象的接口。
*/
public class BufferedInputStream extends FilterInputStream {io
// 被裝飾的對象,已經封裝在父類FilterInputStream中了,故這裏不須要從新封裝了。class
/**
* 將被裝飾的對象傳入進來,這裏被裝飾的對象能夠是InputStream的任何一個子類。
* 換句話說就是,InputStream的任何一個子類均可以被BufferedInputStream包裝。
*/
public BufferedInputStream(InputStream in) {
this(in, DEFAULT_BUFFER_SIZE);
}基礎
public BufferedInputStream(InputStream in, int size) {
super(in);
if (size <= 0) {
throw new IllegalArgumentException("Buffer size <= 0");
}
buf = new byte[size];
}變量
public synchronized int read() throws IOException { if (pos >= count) { fill(); if (pos >= count) return -1; } return getBufIfOpen()[pos++] & 0xff; } }