【问题标题】:Alternative to 1000s of if-then-else statements替代 1000 条 if-then-else 语句
【发布时间】:2023-04-05 09:47:01
【问题描述】:

我正在为 Android 编写一个基于文本的 RPG 游戏,以便让自己熟悉 Java 和 XML。我想在按钮的 ListView 中显示一个字符串选择数组,并且根据用户按下的按钮,我想用一组新的选择相应地更新活动。

例如,假设游戏从以下选项开始:

{option1, option2, option3, option4}

如果用户点击我想要显示的选项 2:

{2-option1, 2-option2, 2-option3, 2-option4}

或者假设用户点击了 4 而不是 2。然后:

{4-option1, 4-option2, 4-option3, 4-option4}

所以,我正在尝试确定一种速度高效/内存高效的方式来确定下一个要显示的String[]

最初我正在考虑构建一个巨大的 if-then-else 树(或 switch 语句 - 没关系),其中每个可能的选项都有一个 if 语句。 例如:

//choice是用户选择的选项

if(choice==option1){
   return {"1-option1", "1-option2", "1-option3"}
}else if(choice== 1-option1 ){
   return {"1-1-option1","1-1-option2","1-1-option3"}

List 会一直持续下去,直到每个可能的选择都返回一个 String[],它对应于要显示的下一组选项。

然后,我开始想也许用对象来做这件事会更干净、更容易:

   MyObject newObject = MyObject(choice)
   newObject.getOptions()

其中choice 是一个构造函数参数,它将String[] 初始化为正确的下一组选项; getOptions() 返回这个String[]

但是,这将是很多对象,我不确定它是否会简化 if/switch 语句方法。

那么,对于处理此类事情的有效方法有什么想法吗?

【问题讨论】:

  • 丑陋、易碎、无法维护。在考虑效率之前,您应该先考虑这些问题。
  • 我同意,这就是为什么我想用适当的结构解决这个“难题”,我认为我提出的 if/switch 语句方法或对象方法是不够的。跨度>
  • 它有2个以上的级别吗?它可以在 XML 中定义并解组为一组分层的选项集对象。
  • 就个人而言,我发现很难从这个示例中辨别出您真正需要做什么。按钮和字符串数组示例不适合我。
  • 听起来像一棵树或图。每个选择都是一个状态,选择是一个转换到新状态的事件。我会选择配置 XML 或 JSON 的状态机。

标签: java android if-statement switch-statement


【解决方案1】:

使用对象内部的Map(可能是HashMap)将"option2"{"2-option1", "2-option2", "2-option3", "2-option4"}相关联。

数据结构的选择在编程中非常重要。

【讨论】:

  • 他返回的是一个数组..所以你需要在hashmap的值侧保留一个数组..不能直接使用{"abcd", "aa", "bb"}跨度>
【解决方案2】:

您将需要一个像 OptionProvider 这样的单例对象,其方法如下:

 - List<Option> getFirstOptions() 
 - List<Option> getNextOptions(Option option)

该对象可以保存有关在 Map&lt;Option,List&lt;Option&gt;&gt; 这样的 Map 中哪些选项位于哪个选项之后的信息。您可以手动填充地图,也可以使用 XML 文件或数据库中的数据进行填充。

然后你可以有一个像 DisplayOptionUtils 这样的实用程序类,其方法如下:

 - String getOptionPrompt(List<Option> chosenOptions, List<Option> nextAvailableOptions)

这将返回您希望您的选项向用户显示的方式(例如,它可以使用 StringBuilder 来创建您需要的内容)。

然后在你的主课中你可以有类似的东西:

List<Option> chosenOptions = new ArrayList<>();
List<Option> nextOptions = OptionProvider.getInstance().getFirstOptions();
while(!nextOptions.isEmpty()) {
  System.out.println(DisplayOptionUtils.getOptionPrompt(chosenOptions, nextOptions);
  Option selectedOption = Option.getByValue(getUserInput());
  chosenOptions.add(selectedOption);
  nextOptions = OptionProvider.getInstance().getNextOptions(selectedOption);
}

这个设计并不完美(我在 10 分钟内想出了它),但希望它能让你了解如何实现你想要的。

【讨论】:

    【解决方案3】:

    将概念转换为更一般的概念:始终存在当前状态,并且可能存在用于该状态的一组选项。选择可以简单地理解为触发状态转换。

    因此,您可以简单地将其在 XML 中建模为:

    <state name="Main Menu">
       <option name="Buy" newState="Shop"/>
    </state>
    <state name="Shop>
       <option name="Exit" newState="Main Menu"/>
    </state>
    

    State 和 Option 可以很容易地建模为类。不需要复杂的代码,只需将所有现有状态放入一个 Map 中。要更改状态,只需向地图询问属于该状态名称的状态并将该状态设置为当前状态...

    【讨论】: