替换行为而不是添加的装饰器模式
Decorator pattern that replace behaviour instead of adding
我阅读了很多帖子并了解到装饰器模式应该为现有对象添加功能。但是,我有一个场景,其中一种行为被替换,而不是扩展。
为了演示,假设我有这些 类:
public interface IDoStuff {
string DoStuff();
string DoOtherStuff();
}
public class A : IDoStuff {
public A(){}
public string DoStuff() {
....
}
public string DoOtherStuff() {
....
}
}
public class B : IDoStuff {
protected readonly IDoStuff decoratee;
public B(IDoStuff decoratee){
this.decoratee = decoratee;
}
public string DoStuff() {
decoratee.DoStuff();
//More code
}
public string DoOtherStuff() {
....
// This does not call decoratee.DoOtherStuff
}
}
虽然我修饰了B.DoStuff
方法,但是它的DoOtherStuff
方法是完全不同的实现,根本不能重用基对象。
我执行得正确吗?或者这是一个完全不同的模式?
装饰器模式使用委托来实现它的方法。在纯版本中:
The decorator forwards requests to the component and may perform additional actions (such as drawing a border) before or after
forwarding. (Design Patterns, GoF, 1997, Decorator pattern)
我们可以推断出装饰器class的每个方法都应该被装饰器使用,并且添加了新方法。看来您没有使用普通的装饰器模式,而只是使用委托模式。这在现实世界中非常常见:您使用不同模式的块构建应用程序以实现固定目标。
不过,更重要的是坚持 Liskov substitution principle:B.doStuff
和 B.doOtherStuff
必须 遵守 IDoStuff
契约(我假设 A.doStuff
和 A.doOtherStuff
会),这样你就可以使用 B
的实例而不是 A
的实例,而不会破坏你的程序逻辑。 (这是 Liskov 替换原则的一个非常模糊的表述,但在这里应该足够了。)
我阅读了很多帖子并了解到装饰器模式应该为现有对象添加功能。但是,我有一个场景,其中一种行为被替换,而不是扩展。 为了演示,假设我有这些 类:
public interface IDoStuff {
string DoStuff();
string DoOtherStuff();
}
public class A : IDoStuff {
public A(){}
public string DoStuff() {
....
}
public string DoOtherStuff() {
....
}
}
public class B : IDoStuff {
protected readonly IDoStuff decoratee;
public B(IDoStuff decoratee){
this.decoratee = decoratee;
}
public string DoStuff() {
decoratee.DoStuff();
//More code
}
public string DoOtherStuff() {
....
// This does not call decoratee.DoOtherStuff
}
}
虽然我修饰了B.DoStuff
方法,但是它的DoOtherStuff
方法是完全不同的实现,根本不能重用基对象。
我执行得正确吗?或者这是一个完全不同的模式?
装饰器模式使用委托来实现它的方法。在纯版本中:
The decorator forwards requests to the component and may perform additional actions (such as drawing a border) before or after forwarding. (Design Patterns, GoF, 1997, Decorator pattern)
我们可以推断出装饰器class的每个方法都应该被装饰器使用,并且添加了新方法。看来您没有使用普通的装饰器模式,而只是使用委托模式。这在现实世界中非常常见:您使用不同模式的块构建应用程序以实现固定目标。
不过,更重要的是坚持 Liskov substitution principle:B.doStuff
和 B.doOtherStuff
必须 遵守 IDoStuff
契约(我假设 A.doStuff
和 A.doOtherStuff
会),这样你就可以使用 B
的实例而不是 A
的实例,而不会破坏你的程序逻辑。 (这是 Liskov 替换原则的一个非常模糊的表述,但在这里应该足够了。)