程序在 Debug 中运行良好,但在 Release 中不行

Posted

技术标签:

【中文标题】程序在 Debug 中运行良好,但在 Release 中不行【英文标题】:Program works fine in Debug, but not in Release 【发布时间】:2016-09-09 13:48:28 【问题描述】:

我做了一个井字游戏,效果很好。最近我决定添加一个重置游戏功能。 这是我从用户那里获取输入的部分

void playerMove() //Gets the player move and updates the box variables

    int boxnumber;
    while(1)      //Set's loop if the player enters a invalid input
    
       cout << "\n Player " << player << "'s turn!(Press 0 to reset the game!): ";
       cin >> boxnumber;
       if(box[boxnumber-1] == 'X' || box[boxnumber-1] == 'O' || boxnumber > 9 || boxnumber < 0) // Checks if the input is valid or not
       
           system("CLS");//If invalid, show error and loop back to start to get new input
           displayBoard();
           cout << "\n Invalid Input! Try again!\n";

       else if(boxnumber == 0)
       
           refreshGame();
           displayBoard();
       else
       
           box[boxnumber-1] = player;//If inputs are fine, set the box variable's and break out of loop!
           break;
       
    


现在,在调试模式下,当我按下 0 时,一切正常并重置游戏,但在发布版本中,当我按下 0 时,它给我“无效输入!再试一次!”

我试过但没用的东西: -重建整个发布和调试版本。 -制作一个新项目并复制粘贴我的代码。同样的事情,调试有效,发布无效。

对于任何想知道的人,我正在使用 code::blocks IDE。编译器是 GNU GCC。 谢谢您的帮助! :)

【问题讨论】:

我觉得你买不到盒子[-1] 当您输入0 时,boxnumber-1 中的box[boxnumber-1] 会是什么? 【参考方案1】:

您有未定义的行为

在“第一个”if 中有box[boxnumber-1],因此当您输入0(正如您在问题中所述)时,您正在尝试访问索引为-1 的元素。那是 UB,因为您正在阅读“无效”内存。

您应该首先检查0(以及负数)。

【讨论】:

感谢您的回答。为什么这在调试中有效但在发布中无效? @JohnMorris11 - 因为“未定义的行为”:) 两种模式下生成的代码不同,内存布局也不同。因此,行为也可能不同。 因为它实际上可能仍然给出了“有效”的结果,只是偶然【参考方案2】:

if 语句中,将范围检查放在值检查之前。也就是改变

if(box[boxnumber-1] == 'X' || box[boxnumber-1] == 'O' || boxnumber > 9 || boxnumber < 0)

if(boxnumber < 0 || box number > 9 || box[boxnumber-1] == 'X' || box[boxnumber-1] == 'O')

这利用了短路:如果输入值小于 0 或大于 9,则不会执行值检查。这样可以避免检查无效的 box[10] 之类的内容。

这仍然存在一个问题:如果用户输入 0,此代码将愉快地检查box[-1],这也超出了范围。要摆脱这种情况,请将测试box number == 0if 语句的分支移到这部分前面:

if (box number == 0)
    // whatever
else if (box[boxnumber-1] == 'X' || box[boxnumber-1] == 'O' || boxnumber > 9 || boxnumber < 0)
    // whatever else

【讨论】:

这是一个很好的修复。从来没有想过这种方式。谢谢你的帮助:) @JohnMorris11 - 另一个建议:从用户那里获取值后,将其递减,以便可接受的值从 0 运行到 8。这将消除数组访问的所有 `-1。跨度>

以上是关于程序在 Debug 中运行良好,但在 Release 中不行的主要内容,如果未能解决你的问题,请参考以下文章

为啥我的程序在发布模式下运行良好,但在调试模式下失败? [关闭]

相机在 Monaca Debugger 中有效,但在 Debug Build 中无效

为啥 spring-boot 应用程序无法在 AWS 中运行,但在本地运行良好?

Hadoop MapReduce 程序在 Eclipse 中运行良好,但在导出到 .jar 文件时运行良好

Apple App Store 中的“应用程序在启动时崩溃”,但它在 Debug/Adhock 中运行良好?

Angular:JWT Token 在 Postman 上运行良好,但在我的应用程序中运行良好