【发布时间】:2017-01-25 23:58:24
【问题描述】:
这可能是一个不好的例子,但请使用它。我有一个超类Cake 和两个子类:ExampleCake 和SaleCake。我还有一个Baker,他可以对蛋糕进行逆向工程以烘烤它的副本,并且知道之后如何处理它。
(全部伪代码)
public class Cake{
radius;
height;
ingredients;
color;
name;
}
public class ExampleCake extends Cake{
shelfLocation;
}
public class SaleCake extends Cake{
owner;
}
public class Baker{
Cake bakeCake(Cake);
Cake bakeSaleCake(Cake, Owner);
Cake bakeExampleCake(Cake, Location);
void handleCake(Cake);
}
面包师需要知道如何处理通用 Cakes、ExampleCakes 和 SaleCakes。所以他的 bakeCake 函数看起来像这样:
Cake bakeCake(cake){
newCake = cake.copy();
mixIngredients(newCake);
putCakeInOven(newCake);
putIcing(newCake);
return cake;
}
Cake bakeSaleCake(cake, owner){
newCake = bakeCake(cake);
newCake.setOwner(owner);
return newCake;
}
Cake bakeExampleCake(cake, location){
newCake = bakeCake(cake);
newCake.setLocation(location);
return newCake;
}
void handleCake(cake){
if(cake instanceof ExampleCake)
putOnShelf((ExampleCake)cake);
else if(cake instanceof SaleCake)
giveToCustomer((SaleCake)cake);
else
putOnTable(cake);
}
我的问题是 Baker 被硬编码为只能处理某些类型的蛋糕。如果出现新类型的蛋糕,他将无法处理它们。是否有一种干净、通用的方法来处理它,或者我上面的伪代码是否有点“足够好”(例如,它不会伤害你的眼睛或心脏)?
谢谢。
【问题讨论】:
-
好像是可克隆模式,你只需要让
Cake类实现复制自己的方法。 -
就蛋糕创作而言是有道理的。我忘了添加“handleCake”部分,我将其附加到伪代码的末尾。
-
handleCake 部分可能可以使用访问者模式重构。
-
像这样在类型上切换是一种代码气味恕我直言。如果您需要知道这样的确切类型,则永远不要“忘记”它。
-
使用访问者模式,我想我仍然会有句柄(SaleCake)和句柄(ExampleCake),所以它仍然是一个类似的问题,无法处理新类型的蛋糕。
标签: java inheritance subclass