3

我正在尝试将用字母编写的电话号码转换为其真正的数字形式。我在 for 循环中有这个 switch 语句,它查看字符串的每个字符,但是 eclipse 说我有重复的情况('G' | 'H' | 'I', 'J' | 'K' | ' L', 'M' | 'N' | 'O') 我不明白为什么?

switch(parts[1].charAt(i)){
   case 'A' | 'B' | 'C' : number.concat("2"); break; 
   case 'D' | 'E' | 'F' : number.concat("3"); break; 
   case 'G' | 'H' | 'I' : number.concat("4"); break; 
   case 'J' | 'K' | 'L' : number.concat("5"); break; 
   case 'M' | 'N' | 'O' : number.concat("6"); break; 
   case 'P' | 'Q' | 'R' | 'S' : number.concat("7"); break; 
   case 'T' | 'U' | 'V' : number.concat("8"); break; 
   case 'W' | 'X' | 'Y' | 'Z' : number.concat("9"); break; 
}
4

3 回答 3

6

有趣的是,我想我知道发生了什么事。

当您这样做时'A' | 'B',您正在对 A 和 B 的字节值进行按位或运算。您的 IDE 检测到一些结果值是等效的。这绝对不是你想做的。

你想要的更像是:

case 'A':
case 'B':
case 'C':
    number.concat("2");
    break;
case 'D':
    [...]

等等。

有关详细信息,请参阅http://docs.oracle.com/javase/tutorial/java/nutsandbolts/switch.html上的“SwitchDemo2” 。

已验证(使用 Python):

>>> ord('G') | ord('H') | ord('I')
79
>>> ord('J') | ord('K') | ord('L')
79
于 2013-10-19T00:42:15.060 回答
5

您的代码中的|字符充当按位 OR 运算符,而是使用switchfallthrough

switch(parts[1].charAt(i)){
    case 'A':
    case 'B':
    case 'C':
        number.concat("2");
    break;
    ...

查看这些字节值的结果

System.out.println('G' | 'H' | 'I');
System.out.println('J' | 'K' | 'L');

都打印 79

引用JLS 14.11

与 switch 语句关联的任何两个 case 常量表达式都不能具有相同的值。

  • 这就是编译器抱怨的原因

阅读switch 教程以了解如何使用 fallthrough

于 2013-10-19T00:42:03.333 回答
0

每个字符都有一个二进制等价物。例如,“G”的二进制值是 01000111。当您应用按位或运算符“|”时,匹配 8 个二进制位中的每一个,如果其中一个为 1,则为 1,如果它们均为 0,则为 0。所以“G” ' | 'H' 相当于将 01000111 的位与 01001000 匹配(H 的二进制表示 - 它们按从 01000001 处的 'A' 开始的顺序排列)。结果是 01001111,转换为十进制后得到 79。如果您通过手动练习,您确实会发现 'G' | 'H' | 'I' 等价于 'J' | 'K' | 'L'。

于 2013-10-19T01:04:14.913 回答