Flash Actionscript 3的Bug?在switch/case语句中使用int和负数会出现问题吗?

20

运行这段代码

var myValue1:int = 2;
switch (myValue1)
{
    case -3: trace(myValue1 + " == -3"); break;
    case -2: trace(myValue1 + " == -2"); break;
    case -1: trace(myValue1 + " == -1"); break;
    case 0:  trace(myValue1 + " == 0"); break;
    case 1:  trace(myValue1 + " == 1"); break;
    case 2:  trace(myValue1 + " == 2"); break;
    case 3:  trace(myValue1 + " == 3"); break;
    default: trace(myValue1 + " is unknown"); break;
}

var myValue2:int = -2;
switch (myValue2)
{
    case -3: trace(myValue2 + " == -3"); break;
    case -2: trace(myValue2 + " == -2"); break;
    case -1: trace(myValue2 + " == -1"); break;
    case 0:  trace(myValue2 + " == 0"); break;
    case 1:  trace(myValue2 + " == 1"); break;
    case 2:  trace(myValue2 + " == 2"); break;
    case 3:  trace(myValue2 + " == 3"); break;
    default: trace(myValue2 + " is unknown"); break;
}

输出结果如下:

2 == 0
-2是未知的

(编译于Flash Builder 4.7.0.349722,运行于Flash 11.5.502.149。运行于Windows 7 SP1,Firefox 18.0.2)

以下更改都可以修复上述问题,给出正确的输出:

  • 将值类型更改为Number
  • 删除负数case语句。
  • case语句更改为使用int变量而不是字面常量...除非这些变量也是const,否则它仍然无法正常工作!

myValue2 = -1更改为myValue2 = -3将会得到输出-1 == -3,同样让人困惑。


显然这是一个bug,但是......是什么导致了它?是否有一些微妙的细节,在使用int或负数case语句时我没有理解?我的代码是否有问题?还是这只是Flash Builder中的字节码编译器问题?


1
发布的代码在Flash CS5和FB4.7中对我来说正常工作。输出:2 == 2,-2 == -2。 - user1901867
1
我没有答案,但通常我会像这样做,而不是一堆if/else语句:switch (true) { case someBooleanExpression: break; case someOtherExpression: break; } 我认为这种行为的答案在于某些东西被强制转换/被视为布尔值。但我不能给出明确的答案,我相信其他人会的 :) - Sunil D.
4
有趣。供您参考,我在Flash Builder 4.7为AIR 3.4构建时得到了相同的结果(我猜测正在使用Flash Player 11.4)。然而,在为Flash Player 9、10.3、11.1、11.2、11.3和11.4编译的Flash Professional CS6中,它会跟踪2 == 2-2 == -2 - david.emilsson
1
Flash CS5:2 == 2-2 == -2 MiniBuilder 2 == 2-2 == -2 wonderfl.net 2 == 2-2 == -2 - khailcs
2
为了确定是Flash Player的错误还是编译器的错误,尝试更改每个版本以确定问题的来源。如果编译器受到指责,您可以尝试使用SWFInvestigator等工具查看输出字节码(以及其中的问题)。 - Antoine Lassauzay
显示剩余10条评论
3个回答

1
你可以通过将原始值转换为字符串,并将case变成字符串值,来迫使编译器按照你的意愿执行。
switch( String(value) )
{
   case "-3": /*do something*/; break;
   case "-2": /*do something*/; break;
   case "-1": /*do something*/; break;
   case  "0": /*do something*/; break;
   case  "1": /*do something*/; break;
   case  "2": /*do something*/; break;
   case  "3": /*do something*/; break;
   default: break;
}

1
我已经提到了几种解决方法,但这与问题无关。 - BlueRaja - Danny Pflughoeft

1
我不认为你会找到这个问题的确切答案。 我能提供的是确认AS3编译器的漏洞性。 我花了很多时间尝试解决类似的“神奇”错误,但最终一无所获。 其中一个例子是For和While循环跳过数组中第一个或最后一个项目,而Foreach循环正常运行。
对我来说,最可信的原因是内存管理错误。 这也可能与硬件有关,因为这种情况发生的频率在我或我的同事使用的某些机器上更高。 我认为一些“隐形”的条件得到满足,例如执行操作的顺序(您可以尝试在var声明和switch之间放置一些虚拟代码,或者将var值分配几次,只是为了“激活内存”),再加上容易出错的编译器混乱了内存寻址,因此您的switch认为它正在比较两个整数,而实际上它从内存中得到了一个不同的值。

1
这只是Flash Builder中字节码编译器的问题。显然,您的语法没有问题;自2005年以来,已知有数百个编译器问题仍未解决。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接