使用接口的具体变体重载Java方法



我有一个类,它有一个函数,我希望根据操作的不同表现不同,所有这些具体的类都实现了Action类。我知道,由于重载是在运行时确定的,Action a不会进入这些函数中的任何一个。在不使用instanceof的情况下,正确的方法是什么?

谢谢!

// public State myDoAction(Action action){
//    return myDoAction(action);
// }
public State myDoAction(Rest action){
Witch newMe = me.doAction(action);
return new State(newMe,opponent,potionsList);
}
public State myDoAction(Cast action){
Witch newMe = me.doAction(action);
return new State(newMe,opponent,potionsList);
}
public State myDoAction(Brew action){
Witch newMe = me.doAction(action);
List<Brew> newPotionsList = new ArrayList<>(potionsList);
newPotionsList.remove(action);
return new State(newMe,opponent,newPotionsList);
}

如果我理解正确的话,你有一个带有doAction(Action a)方法的类Witch,以及几个改变游戏StateAction

我认为这样组织代码是一个错误

public class Witch {
public State doAction(ActionSubtype1 a) { ... }
public State doAction(ActionSubtype2 a) { ... }
// ... other stuff here ...
}

因为它会迫使您在每次包含新操作时更改Witch类。相反,应该由Actions根据需要更改State(或者创建并返回新的States,而不是实际更改它们(:

public interface Action {
public State changeState(State current)
}

State应该提供对游戏中所有信息的访问,包括药剂、当前回合、有什么Witches等等。然后,你的Witch类不再知道或关心动作,因为它们可以在游戏级别处理:

public class Witch {
// ... other stuff here ...
public List<Action> getActions(State s) {
// returns valid actions for the current state of the game
}
}
public class Game {
// ... other stuff here ...
public void play(State initialState) {
State s = initialState;
while ( ! s.isGameOver()) {
Witch w = s.getCurrentPlayer();
Action a = letPlayerChoose(w.getActions(s));
s = a.changeState(s);
}
}
}

您可以简单地将方法"myDoAction";在Action接口(或抽象类(中,然后在子类中重载它。

像这样:

public interface Action {
State myDoAction ();
}

public class Rest implements Action {
public State myDoAction(){
Witch newMe = me.doAction();
return new State(newMe,opponent,potionsList);
}
}

public class Cast implements Action {
public State myDoAction(){
Witch newMe = me.doAction();
return new State(newMe,opponent,potionsList);
}
}

public class Brew implements Action {
public State myDoAction(){
Witch newMe = me.doAction();
List<Brew> newPotionsList = new ArrayList<>(potionsList);
newPotionsList.remove(action);
return new State(newMe,opponent,newPotionsList);
}
}

显然,您需要将方法所需的对象传递给";myDoAction";解密(或将它们设置为实例成员(

最新更新