【问题标题】:Java Switch Statement - Is "or"/"and" possible?Java Switch 语句 - “或”/“和”可能吗?
【发布时间】:2012-04-10 14:31:24
【问题描述】:

我实现了一个字体系统,它通过 char switch 语句找出要使用的字母。我的字体图像中只有大写字母。我需要做到这一点,例如,'a' 和 'A' 都具有相同的输出。与其有 2 倍的案例数量,不如是以下内容:

char c;

switch(c){
case 'a' & 'A': /*get the 'A' image*/; break;
case 'b' & 'B': /*get the 'B' image*/; break;
...
case 'z' & 'Z': /*get the 'Z' image*/; break;
}

这在java中可能吗?

【问题讨论】:

  • 我只想指出,我已经很久没有使用 switch 语句了,而且我几乎每天都在编写 Java。原因是我觉得它的风格很糟糕,因为它有点像 goto,而且总是有一个我更喜欢的不同解决方案。在您的情况下,您可以使用 Map 或枚举(这通常是一个很好的替代品)与 boolean matches(char c) 和 File getImage() 方法
  • @MichaelSchmeißer 在这种情况下,您可能还想重新考虑使用 for/while 循环,因为它们是 Goto /s 的另一种形式。这就是为什么它们还包含中断/继续关键字。严肃地说,'switch' 不是 goto,因为它提供了自己的块作用域。它只是工具箱中的另一个工具,对于这个特定的用例,它也是最合适的。

标签: java char switch-statement


【解决方案1】:

观察一个有趣的Switch case 陷阱 --> fall through of switch

“break 语句是必要的,因为没有它们,switch 块中的语句就会失败:” Java Doc's example

没有break的连续case的片段:

    char c = 'A';/* switch with lower case */;
    switch(c) {
        case 'a':
            System.out.println("a");
        case 'A':
            System.out.println("A");
            break;
    }

这种情况的 O/P 是:

A

但是如果你改变 c 的值,即char c = 'a';,那么这会变得有趣。

这种情况的 O/P 是:

a A

即使第二种情况测试失败,程序也会继续打印A,因为缺少break,这导致switch 将其余代码视为一个块。匹配的case标签之后的所有语句都按顺序执行。

【讨论】:

    【解决方案2】:

    您可以通过省略break; 语句来使用switch-case fall through。

    char c = /* whatever */;
    
    switch(c) {
        case 'a':
        case 'A':
            //get the 'A' image;
            break;
        case 'b':
        case 'B':
            //get the 'B' image;
            break;
        // (...)
        case 'z':
        case 'Z':
            //get the 'Z' image;
            break;
    }
    

    ...或者您可以在switching 之前标准化为lower caseupper case

    char c = Character.toUpperCase(/* whatever */);
    
    switch(c) {
        case 'A':
            //get the 'A' image;
            break;
        case 'B':
            //get the 'B' image;
            break;
        // (...)
        case 'Z':
            //get the 'Z' image;
            break;
    }
    

    【讨论】:

    • 啊,谢谢你的例子。我之前想过将输入字符串全部大写,但不知道这怎么可能,所以也感谢第二个示例。
    • 实际上,如果c 的情况需要保留,我会将toUpperCase 放在开关内。但是 +1 因为这节省了很多不必要的 case 语句:-)
    【解决方案3】:

    根据我对您的问题的了解,在将字符传递到 switch 语句之前,您可以将其转换为小写。所以你不必担心大写,因为它们会自动转换为小写。 为此,您需要使用以下功能:

    Character.toLowerCase(c);
    

    【讨论】:

      【解决方案4】:

      以上都是很好的答案。我只是想补充一点,当有多个字符要检查时,if-else 可能会更好,因为您可以改为编写以下内容。

      // switch on vowels, digits, punctuation, or consonants
      char c; // assign some character to 'c'
      if ("aeiouAEIOU".indexOf(c) != -1) {
        // handle vowel case
      } else if ("!@#$%,.".indexOf(c) != -1) {
        // handle punctuation case
      } else if ("0123456789".indexOf(c) != -1) {
        // handle digit case
      } else {
        // handle consonant case, assuming other characters are not possible
      }
      

      当然,如果这变得更复杂,我建议使用正则表达式匹配器。

      【讨论】:

      • == 0 不正确。也就是说“c 是字符串的第一个字符吗?”,您可能想要>= 0!= -1
      • @dbaupp:哎呀,你是对的。我在考虑 compareTo() 而不是 indexOf()。固定。
      • 其中一些测试可以替换为Character 中的现有方法,例如“is digit”案例。
      【解决方案5】:

      上面,您的意思是 OR 不是 AND。 AND 示例:110 & 011 == 010 这不是您要查找的内容。

      对于 OR,只有 2 例没有 1 号休息。例如:

      case 'a':
      case 'A':
        // do stuff
        break;
      

      【讨论】:

      • 我不知道第一点对 OP 有多大帮助。
      • @MДΓΓБДLL:关于 AND 的评论说明了为什么 OP 想要 OR 而不是 AND。 OR 部分与接受的答案相同,所以我希望它是相关的。
      猜你喜欢
      • 1970-01-01
      • 2016-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-07-31
      • 2016-03-02
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多