奇怪的无限循环

时间:2014-11-03 16:24:01

标签: c++ infinite-loop

我正在查看另一个问题,即用户提交了一些段错误的代码 这段代码有一个循环尝试写入超出范围的数组索引,作为我检查代码的一部分,我尝试编译并运行它。 (OP报告说它正在写一个文件 - 只是在超出边界循环之后的代码中才出现这种情况。)

我添加了一些printf()语句(是的,我知道,C ++,使用std::cout,但我保留了他们使用过的)来跟踪进度在运行时,然后我编译并运行它。

我没有输出。

这很奇怪,所以除了有问题的循环之外,我完全删除了。这是我运行的确切代码:

#include <iostream>
#include <cstdlib>
#include <cstdio>
#include <fstream>

#define m 17
#define n 17
using namespace std;


int main(){
    double f0[n][m],f[n][m],x[n],y[m];
    double dx, time, dy, dt, alpha, mstep, termx, termy, dd;
    dx = 1.0;
    dy = 1.0;
    dt = 0.20;
    alpha = 0.20;
    mstep = 200;
    FILE * mFile;

    for(int j=0; j<m; j++){
        printf("running: j = %d\n",j);    //***                          I added this line
        for(int i=0; i<n+1; i++){
            f0[i][j] = 0.0;
            f[i][j] = 0.0;
            if (i == n && j == m-1){ printf("Will this crash now?\n");}//I added this line
        }
    }
    printf("made it out without crashing");                            //I added this line


    return 0;   
}

我期待以下输出(此时评论为***的行没有出现:

Will this crash now?
Segmentation-fault... (blah blah blah)

相反,什么也没有,控制没有被释放 添加***行后,我再次运行程序:

...
running: j = 1
running: j = 2
running: j = 3
running: j = 4
running: j = 5
running: j = 1
running: j = 2
running: j = 3
running: j = 4
running: j = 5
running: j = 1
...

这很奇怪。在for-loop标头中,j之外的j++应该没有分配,但它在某个时候被重置。

我编译并运行了很多次以防它出现故障,没有任何变化。然后,我按照最初在question中发布的完整代码运行,但添加了额外的printf语句。
j周期现在从1到15。

进一步的测试显示代码的长度以某种方式改变了周期的周期。

The code posted in this question: 33 lines, 1- 5 repeated.
The original code posted:         98 lines, 1-15 repeated.
Removing bottom two loops:        71 lines, 1-10 repeated.

这是一个编译器错误,或者我是盲目的并且在j某处做了一些分配而完全错过了它?

有人甚至可以重现这个吗?

编译器:GCC 4.8.2在Cygwin下运行。

2 个答案:

答案 0 :(得分:3)

您假设根据您的检查仅在i == n && j == m-1之后才会发生越界访问,但实际上它会更早发生。第一次越界访问发生的时间是j==0 && i==n。之后,所有赌注都已关闭。程序可能会崩溃,进入无限循环或执行其他操作。

答案 1 :(得分:2)

这个循环几乎肯定是错误的:

    for(int i=0; i<n+1; i++){
       f0[i][j] = 0.0;
        f[i][j] = 0.0;

因为主要维度为n,因此您将迭代超出数组边界。

你要么:

    for(int i=0; i<n; i++){

或者您需要将数组维度增大1。

否则未定义的行为只是 - undefined。