【问题标题】:My c++ program has stopped working我的 c++ 程序已停止工作
【发布时间】:2017-09-19 12:08:30
【问题描述】:

我试图在具有连续数字的矩阵中找到给出正确答案的最长路径。函数调用递归执行,直到附近没有连续数字,并且每次检查单元格是否被访问

#include<bits/stdc++.h>
#define n 3
using namespace std;

// Returns length of the longest path beginning with mat[i][j].
// This function mainly uses lookup table dp[n][n]
int findLongestFromACell(int i, int j, int mat[n][n], int dp[n][n])
{
    // Base case
    if (i<0 || i>=n || j<0 || j>=n)
        return 0;

    // If this subproblem is already solved
    if (dp[i][j] != -1)
        return dp[i][j];

    // Since all numbers are unique and in range from 1 to n*n,
    // there is atmost one possible direction from any cell
    if (j<n-1 && ((mat[i][j] +1) == mat[i][j+1]))
       return dp[i][j] = 1 + findLongestFromACell(i,j+1,mat,dp);

    if (j>0 && (mat[i][j] +1 == mat[i][j-1]))
       return dp[i][j] = 1 + findLongestFromACell(i,j-1,mat,dp);

    if (i>0 && (mat[i][j] +1 == mat[i-1][j]))
       return dp[i][j] = 1 + findLongestFromACell(i-1,j,mat,dp);

    if (i<n-1 && (mat[i][j] +1 == mat[i+1][j]))
       return dp[i][j] = 1 + findLongestFromACell(i+1,j,mat,dp);

    // If none of the adjacent fours is one greater
    return dp[i][j] = 1;
}

// Returns length of the longest path beginning with any cell
int finLongestOverAll(int mat[n][n])
{
    int result = 1;  // Initialize result

    // Create a lookup table and fill all entries in it as -1
    int dp[n][n];
    memset(dp, -1, sizeof dp);

    // Compute longest path beginning from all cells
    for (int i=0; i<n; i++)
    {
      for (int j=0; j<n; j++)
       {
          if (dp[i][j] == -1)
             findLongestFromACell(i, j, mat, dp);

          //  Update result if needed
          result = max(result, dp[i][j]);
       }
     }

     return result;
}

// Driver program
int main()
{
   int  mat[n][n] = {{1, 10, 9},
                    {5, 3, 8},
                    {4, 6, 7}};
   cout << "Length of the longest path is "
        << finLongestOverAll(mat);
   return 0;
}

但是当我尝试相同的代码来查找二进制矩阵中的最长路径时,程序停止执行

#include<bits/stdc++.h>
#define n 3
using namespace std;

// Returns length of the longest path beginning with mat[i][j].
// This function mainly uses lookup table dp[n][n]
int findLongestFromACell(int i, int j, int mat[n][n], int dp[n][n])
{
    // Base case
    if (i<0 || i>=n || j<0 || j>=n)
        return 0;

    // If this subproblem is already solved
    if (dp[i][j] != -1)
        return dp[i][j];

    // Since all numbers are unique and in range from 1 to n*n,
    // there is atmost one possible direction from any cell
    if (j<n-1 && (1 == mat[i][j+1]))
       return dp[i][j] = 1 + findLongestFromACell(i,j+1,mat,dp);

    if (j>0 && (1 == mat[i][j-1]))
       return dp[i][j] = 1 + findLongestFromACell(i,j-1,mat,dp);

    if (i>0 && (1 == mat[i-1][j]))
       return dp[i][j] = 1 + findLongestFromACell(i-1,j,mat,dp);

    if (i<n-1 && (1 == mat[i+1][j]))
       return dp[i][j] = 1 + findLongestFromACell(i+1,j,mat,dp);

    // If none of the adjacent fours is one greater
    return dp[i][j] = 1;
}

// Returns length of the longest path beginning with any cell
int finLongestOverAll(int mat[n][n])
{
    int result = 1;  // Initialize result

    // Create a lookup table and fill all entries in it as -1
    int dp[n][n];
    memset(dp, -1, sizeof dp);

    // Compute longest path beginning from all cells
    for (int i=0; i<n; i++)
    {
      for (int j=0; j<n; j++)
       {
          if (dp[i][j] == -1)
             findLongestFromACell(i, j, mat, dp);

          //  Update result if needed
          result = max(result, dp[i][j]);
       }
     }

     return result;
}

// Driver program
int main()
{
   int  mat[n][n] = {{1, 0, 0},
                    {1, 0, 0},
                    {1, 1, 1}};
   cout << "Length of the longest path is "
        << finLongestOverAll(mat);
   return 0;
}

此代码中的错误是什么。提前致谢

【问题讨论】:

  • edit您的问题提供minimal reproducible example
  • 不包含,它是一个私有的非标准标头,不包含在内。不要#define 整数常量。
  • 您确定它停止工作了吗?你是怎么确定的?也许执行需要很长时间才能完成。
  • @FrançoisAndrieux 只需要几个 epoch 就可以无限递归最终溢出堆栈?
  • 这段代码看起来很糟糕。如果您将这个几乎 C 重构为使用 C++ 标准库容器,您可以使用 .at() 方法(而不是 operator[])并在不使用调试器的情况下捕获潜在的索引错误。即使没有,重构代码也会对其他读者有所帮助。

标签: c++ recursion matrix longest-path


【解决方案1】:

您的算法有问题。你依赖的事实是

任何单元格最多有一个可能的方向

而且这条路永远不可能是圆形的。

在二进制矩阵的情况下,条件必然会失败。 您从 (0,0) 到 (1,0) 到 (0,0) 到 (1,0) 到 (0,0) 到 (1,0) 到 (0,0) 到 (1,0)到 (0,0) 到 (1,0) 到 (0,0) 到 (1,0) 到 (0,0) 到 (1,0) 到 (0,0) 到 (1,0) 到 ( 0,0) 到 (1,0) 到 (0,0) 到 (1,0) 到 (0,0) 到 (1,0) 到 (0,0) 到 (1,0) 等等: -)

因此,您的算法会在堆栈已满时终止,因为您选择的最长路径长度是无限的,并且只有 Chuck Norris 可以在有限时间内执行无限循环。

编辑:我强烈支持 Xeverous 的评论。你真的应该将你的代码重构为更多的 C++。这使代码更易于阅读,并且您很容易发现问题。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2013-11-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-03-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多