我正在研究一个具有几种不同类型动物的动物园的示例。用户输入命令“添加老虎”,然后将老虎添加到动物园。
在我的命令解释器类中,我有一些类似以下的代码:
String animalName...
Animal newAnimal;
if (animalName.equals("tiger"))
newAnimal = new Tiger();
else if (animalName.equals("elephant"))
newAnimal = new Elephant();
这里的问题是,当将一种新的动物添加到程序中时,也必须更改这段代码。我只想通过子类化Animal来添加新动物,而无需更改现有类中的任何东西。
用户在其命令中给定的名称不一定与动物的类名相同(例如,“添加孟加拉虎”将添加一个孟加拉虎对象)。
如果可能的话,我宁愿避免使用反射。
这是最终代码:
private static String getClassName(String name) {
char ch;
int i;
boolean upper = true;
StringBuilder s = new StringBuilder("animals.");
for (i=0; i<name.length(); i++) {
ch = name.charAt(i);
if (ch!=' ') {
if (upper)
s.append(Character.toUpperCase(ch));
else
s.append(Character.toLowerCase(ch));
upper = false;
} else
upper = true;
}
return s.toString();
}
@Override
public Animal addAnimal(String s) {
try {
Animal animal = (Animal)Class.forName(getClassName(s)).newInstance();
addAnimal(animal);
return animal;
} catch (InstantiationException e) {
throw new IllegalArgumentException("There are no animals called like this");
} catch (IllegalAccessException e) {
throw new IllegalArgumentException("There are no animals called like this");
} catch (ClassNotFoundException e) {
throw new IllegalArgumentException("There are no animals called like this");
} catch (ClassCastException e) {
throw new IllegalArgumentException("There are no animals called like this");
}
}
最佳答案
您应该使用动态类加载:Class.forName(name)
,例如:
String animal = ... // e.g. elephant
String className = "com.mycompany.animals." + animal.substring(0, 1).toUpperCase() + animal.subString(1);
Animal obj = (Animal)Class.forName(className);