依賴注入的整個點(至少據我所知)是Button
不需要知道它正在切換的具體SwitchableDevice
。
的抽象接口看起來是這樣的:
struct SwitchableDevice {
virtual void switchOn() = 0;
virtual void switchOff() = 0;
};
而且按鈕可以這樣實現:
struct Button {
SwitchableDevice& dev;
bool state = false;
Button(SwitchableDevice& d) : dev(d) {}
void buttonPress(){
if (state) { dev.switchOff(); }
else { dev.switchOn(); }
state = !state;
}
};
對於按鈕,這就是它!沒有人需要告訴按鈕SwitchableDevice
的具體實現是什麼,換句話說:Button
和SwitchableDevice
的實現是分離的。
一種可能實現一個Lamp
的看起來是這樣的:
struct Lamp : SwitchableDevice {
void switchOn(){std::cout << "shine bright" << std::endl;}
void switchOff(){std::cout << "i am not afraid of the dark" << std::endl;}
};
而且,可以這樣使用:
int main(){
Lamp lamp;
Button button(lamp);
button.buttonPress();
button.buttonPress();
}
希望幫助...
的benifit是現在我們可以單獨更改Button
和Lamp
的實現,而不必在另一部分上更改任何內容。例如,一個ButtonForManyDevices
看起來是這樣的:
struct ButtonForManyDevices {
std::vector<SwitchableDevice*> devs;
bool state = false;
Button(std::vector<SwitchableDevice*> d) : devs(d) {}
void buttonPress(){
if (state) for (auto d: devs) { d.switchOff(); }
else for (auto d: devs) { d.switchOn(); }
state = !state;
}
};
而且同樣,你可以無需更改按鈕上的任何徹底改變Lamp
的行爲(的SwitchableDevice
範圍內,當然同樣ButtonForManyDevices
甚至可能。用於切換Lamp
,VaccumCleaner
和MicroWaveOven
@ tobi303 Button'使用抽象類來代替具體的東西,這意味着'Button'不再取決於'Lamp'(或任何具體的東西)。第一個例子,'Button'需要'Lamp',這意味着高級對象取決於低級別對象,級別的對象。取而代之的是反轉:取決於高級對象的低級對象。這正是你想要的DIP。據我讀過這本書,我沒有看到任何**的例子,你會告訴按鈕具體實現它要使用 –
給我一秒鐘我會寫一個答案。在評論中已經太多了blabla;) – user463035818
這是我的問題:誰告訴'Button'它應該使用什麼'SwitchableDevice'的具體實現? –