我一直在讀這個「demeter法」的東西,它(和純粹的「包裝」類一般)似乎通常是反模式。考慮一個實現類:包裝/ demeter定律似乎是反模式
class FluidSimulator {
void reset() { /* ... */ }
}
現在考慮另一個類的兩種不同的實現:
class ScreenSpaceEffects1 {
private FluidSimulator _fluidDynamics;
public FluidSimulator getFluidSimulator() { return _fluidDynamics; }
}
class ScreenSpaceEffects2 {
private FluidSimulator _fluidDynamics;
public void resetFluidSimulation() { _fluidDynamics.reset(); }
}
,並調用方式表示方法:
callingMethod() {
effects1.getFluidSimulator().reset(); // Version 1
effects2.resetFluidSimulation(); // Version 2
}
乍一看,第2版似乎更簡單一些,並遵循「Demeter規則」,隱藏Foo的實現等等,但是這將FluidSimulator中的所有更改都聯繫到了ScreenSpaceEffects。例如,如果一個參數添加的復位,然後我們有:
class FluidSimulator {
void reset(bool recreateRenderTargets) { /* ... */ }
}
class ScreenSpaceEffects1 {
private FluidSimulator _fluidDynamics;
public FluidSimulator getFluidSimulator() { return _fluidDynamics; }
}
class ScreenSpaceEffects2 {
private FluidSimulator _fluidDynamics;
public void resetFluidSimulation(bool recreateRenderTargets) { _fluidDynamics.reset(recreateRenderTargets); }
}
callingMethod() {
effects1.getFluidSimulator().reset(false); // Version 1
effects2.resetFluidSimulation(false); // Version 2
}
在這兩個版本,callingMethod需要改變,但在第2版,ScreenSpaceEffects 也需要改變。有人可以解釋具有包裝器/外觀的優點(除適配器外或包裝外部API或暴露內部API)。
編輯:其中一個我碰到這個,而不是一個微不足道的例子的實例。
你的意思是「版本2似乎更簡單」? – 2010-03-31 06:54:07
是的,很抱歉,會改變 – 2010-03-31 06:57:14
版本1不遵循德米特的規則。輸錯? – Corwin 2010-03-31 06:58:24