【发布时间】:2012-11-20 09:41:02
【问题描述】:
假设我们有一个 Car 对象。 acceleration 和 breaking 功能是使用 strategy pattern 实现的。但是,如果我们想将硝基气体功能引入现有的汽车对象,该怎么办?我可以使用什么设计模式?
我想在创建汽车对象后添加硝基特征(属性)。
【问题讨论】:
标签: java oop design-patterns
假设我们有一个 Car 对象。 acceleration 和 breaking 功能是使用 strategy pattern 实现的。但是,如果我们想将硝基气体功能引入现有的汽车对象,该怎么办?我可以使用什么设计模式?
我想在创建汽车对象后添加硝基特征(属性)。
【问题讨论】:
标签: java oop design-patterns
您可以查看Decorator pattern,它可用于为现有对象动态添加功能。
【讨论】:
装饰器模式可以动态地为对象添加不同的功能。但是这些功能必须在具体装饰器中实现。开发人员可以决定在运行时添加哪些功能。
【讨论】:
在静态类型语言中,您不能在运行时向对象添加方法。编译器遇到类似 car.nitroAccelerate() 的语句时,会检查汽车对象是否实现了任何具有 nitroAccelerate 方法的接口。如果您可以在运行时添加(或删除)方法,则不可能进行此类检查。
动态语言允许在运行时添加方法。但这有一个缺点,当你在代码中放入car.nitroAccelerate()时,你需要仔细分析这里的汽车对象是否有这样的方法。
您可以在运行时使用装饰器来修改现有方法,但这样做,您并没有修改现有对象,只是创建一个包装旧对象的新对象。
所以如果你这样做:
Car fasterCar = new CarWithNitro(car);
并且你的一些代码仍然包含对原车的引用,这辆原车不会更快,因为包装的行为不会修改原车。
【讨论】:
如果你想添加新方法,你需要创建一个新的子类和/或使用委托。如果“nitro”功能需要显式调用方法来激活,这将是必要的。
但是,如果您只想在不添加方法的情况下添加现有功能,那么 Decorator 是一个不错的选择。假设接口“Car”有一个名为 floorIt() 的方法。在这种情况下,您可以使用 Decorator 向 floorIt 添加“nitro kick”,而无需添加到 Car 接口。
当然,有一个中间立场。如果您使用运行时类型发现和/或多个接口,您既可以使用装饰器,也可以向结果对象添加方法。
【讨论】: