我有一个静态私有java方法,已经在包含类的许多地方使用过。
类似于:
private static ColoredItem createItem(Object obj, Color background, Color foreground) {
ColoredItem item = new ColoredItem();
//Some logic goes here to paint the item
//Some other logic to apply the background and foreground colors
return item;
}
我的问题是,从一个好的设计角度来看,在第一个参数实现特定接口的情况下,忽略作为参数传递给参数的颜色是否合适?
因此该方法将被修改为:
private static ColoredItem createItem(Object obj, Color background, Color foreground) {
ColoredItem item = new ColoredItem();
//Some logic goes here to paint the item
//Some other logic to apply the background and foreground colors
if(obj instanceof SOME_INTERFACE) {
item.setBackgroundColor(some other color);
item.setForegroundColor(some other color);
}
return item;
}
答案 0 :(得分:2)
我会使用一个单独的方法,适当地记录它,然后使用新参数调用现有方法。它应该工作,当然取决于您的实际对象层次结构。
private static ColoredItem createItem(SOME_INTERFACE obj) {
return createItem(obj, newColor1, newColor2);
}
答案 1 :(得分:2)
一般instanceof
,这是因为instanceof是运行时检查,但你有很多方法可以在编译时选择适当的行为。
如果允许您在编译时知道您正在处理的变量的类型,那么您可以让 method overloading 执行脏工作:
ColoredItem createItem(SomeInterface obj, Color background, Color foreground) {
ColoredItem item = createItem(obj);
item.setBackground(...);
}
ColoredItem createItem(GenericItem obj) {
...
}
答案 2 :(得分:2)
从设计角度来看,最好避免使用instanceof
运算符,并使用声明的接口类型作为obj
参数类型。
声明一个界面,让我们说MyCustomInterface
public interface MyCustomInterface {
public void setBackgroundColor(int color);
public void setForegroundColor(int color);
}
并声明
private static ColoredItem createItem(MyCustomInterface obj) {
ColoredItem item = new ColoredItem();
int bgColor = ....
int color = ....
obj.setBackgroundColor(bgColor);
obj.setForegroundColor(color);
return item;
}
甚至更好的方式:
将MyCustomInterface
参数添加到ColoredItem
构造函数中。在类ColoredItem
中声明默认背景和前景色。如果参数中未指定这些颜色,请使用它们。
然后使用:
private static ColoredItem createItem(MyCustomInterface obj) {
return new ColoredItem(obj);
}
答案 3 :(得分:2)
不,不是。一个好的设计选项是使用重载:
private static ColoredItem createItem(Interface1 obj, Color background, Color foreground){
// do something here that require the two parameters
}
private static ColoredItem createItem(Interface2 obj) {
/// do something for the object that do not require the two other parameters
}
这样,您就可以避免检查第一个参数的类型。运行时将为您执行此操作。此外,代码将更清晰,因为现在这个方法的用户将确切知道要传递给它的内容。
我希望这有帮助, -Caius
答案 4 :(得分:1)
我猜参数'background'和'foreground'将在'some other logic'中设置为ColoredItem,无论obj是什么。 所以我想这样做:
public interface CustomInterface{
Color getBackgroundColor(Color orginBackground);
Color getForegroundColor(Color orginForeground);
}
private static ColoredItem createItem(CustomInterface obj, Color background, Color foreground) {
ColoredItem item = new ColoredItem();
//Some logic goes here to paint the item
//Some other logic to apply the background and foreground colors
item.setBackgroundColor(obj.getBackgroundColor(background));
item.setForegroundColor(obj.getForegroundColor(foreground));
return item;
}
答案 5 :(得分:0)
我没有重载构造函数(你可以做什么,当然)我建议你使用Builder Pattern,它允许你根据你拥有的参数确定如何构建你的对象:
https://en.wikipedia.org/wiki/Builder_pattern
构建器模式是对象创建软件设计模式。 与抽象工厂模式和工厂方法模式不同 其目的是为了实现多态性的目的 构建器模式是找到伸缩构造函数的解决方案 反模式。伸缩构造器反模式发生时 对象构造函数参数组合的增加导致了 指数的构造函数列表。而不是使用众多 构造函数,构建器模式使用另一个对象,构建器,即 逐步接收每个初始化参数,然后返回 一次产生的构造对象。
我在使用谷歌的一些类时在很多java代码中发现了这种模式,从那以后我就成了一个大粉丝。
答案 6 :(得分:0)
我建议将if
条件移到Factory类。这是一个伪实现。
ColoredItemFactory
将返回具有create方法的ColoredItem
接口的实现。
ColoredItem界面:
interface ColoredItem {
}
class AColoredItem implements ColoredItem{
AColoredItem(Color... colors) {
// Do something specific to A here
}
}
class BColoredItem implements ColoredItem{
BColoredItem(Color... colors) {
// Do something specific to B here
}
}
ColoredItemFactory:
class ColoredItemFactory {
public static ColoredItem getColoredItem(ColoredItemType type, Color... colors) {
switch(type) {
case A:
return new AColoredItem(Color... colors);
break;
case B:
return new BColoredItem(Color... colors);
break;
}
}
}
enum ColoredItemType {
A,B;
}
ColoredItemFactory将返回ColoredItem的正确实现。 ColoredItemType枚举帮助ColoredItemFactory找出正确的实现类。希望这有帮助!