当前位置: 首页 > 知识库问答 >
问题:

在路径单元格和等于“和”的2D数组中查找“路径”

东郭展
2023-03-14

给定二维正整数数组。“路径”是相邻单元格的集合。两个单元格仅从右/左/上/下(无对角线)相邻。

任务是编写一个函数,用于接收2D数组、整数和2D数组路径(与mat大小相同-空数组均为零)。

函数应检查单元格总和等于sum的路径是否存在,如果存在,则应返回true,否则返回false。

数组路径将标记路径(如果存在路径,则标记路径为1)。

例如,如果mat是:

和总和=4

然后,路径可以是以下三种路径之一:

我的代码:

public static void main(String[] args) 
{
    int[][] mat={{2,41,3,14},
                 {2,1,24,7},
                 {2,15,10,54},
                 {63,22,2,4}};

    int[][] path={{0,0,0,0},
                  {0,0,0,0},
                  {0,0,0,0},
                  {0,0,0,0}};
    findSum(mat,4,path);
    //print(mat);
    print(path);
}
public static boolean findSum (int mat[][], int sum, int path[][])
{
    return findSum(mat,sum,path,0,0);
}

public static boolean findSum (int mat[][], int sum, int path[][],int i,int j)
{
    if(sum==0)                      
        return true;

    if(i==mat[0].length||j==mat[1].length)
        return false;       
    boolean result=findSum(mat,sum-mat[i][j],path,i,j+1)||findSum(mat,sum-mat[i][j],path,i+1,j);

    if(result)
        path[i][j]=1;
    return result;

}
private static void print(int[][] arr)
{
    for(int i=0;i<arr[0].length;i++)
    {
        for(int j=0;j<arr[0].length;j++)
        {
            System.out.print(arr[i][j]+" ");
        }
        System.out.println();
    }
}

只有当路径从(0,0)开始时,我的代码才能正常工作,但对其他路径不起作用,例如,即使存在这样的路径,它也不起作用(路径数组都为零)。

注:

  • 函数必须是递归的-根本没有循环。
  • 不允许全局变量(打印数组不是问题的一部分-仅用于测试,因此有一个循环)

共有1个答案

公西国发
2023-03-14

问得好。。。以下是答案。这是一个有趣的代码挑战;)

public static void main(String[] args) 
{
    int[][] mat={{2,41,3,14},
                 {2,1,24,7},
                 {2,15,10,54},
                 {63,22,2,4}};

    int[][] path={{0,0,0,0},
                  {0,0,0,0},
                  {0,0,0,0},
                  {0,0,0,0}};

    if ( findSum(mat,22,path) ) print(path);
    else System.out.println("No path found");
}
public static boolean findSum (int mat[][], int sum, int path[][])
{
    return startPath(mat, sum, path, -1, 0);
}

// Recursively check every possible starting point
public static boolean startPath(int mat[][], int sum, int path[][], int y, int x)
{
    // Iterate y, goto next column if necessary
    if (++y == mat.length) {
        y = 0;
        ++x;
    }

    if (x == mat[0].length) // Bounds check
        return false;

    if (findSum(mat, sum, path, y, x)) // We've found a successful start point!
    {
        System.out.println("A successful path starts at " + x + ", " + y);
        return true;
    }

    return startPath(mat, sum, path, y, x); // We'll have to keep looking
}

public static boolean findSum (int mat[][], int sum, int path[][], int i, int j)
{
    if(i==mat[0].length || j==mat[1].length || i<0 || j<0) // Bounds check
        return false;

    if (path[i][j] == 1) // Backtracking check
        return false;

    sum -= mat[i][j]; // Decrement sum

    if (sum >= 0) { // More to go? look around
        path[i][j] = 1;

        if (sum == 0) return true; // We made it!

         // If any path finds the end, don't try other paths
        boolean result = findSum(mat, sum, path, i+1, j);
        if (result) return true;
        result = findSum(mat, sum, path, i, j+1);
        if (result) return true;
        result = findSum(mat, sum, path, i-1, j);
        if (result) return true;
        result = findSum(mat, sum, path, i, j-1);

         // There was no successful paths, this is a dead end
        if (!result) path[i][j] = 0;
        return result;
    } else { // We're negative, overshot it
        return false;
    }
}

private static void print(int[][] arr)
{
    for(int i=0;i<arr[0].length;i++)
    {
        for(int j=0;j<arr[0].length;j++)
        {
            System.out.print(arr[i][j]+" ");
        }
        System.out.println();
    }
}

顺便说一下,当检查多维数组维度时,您的意思是做arr.length和arr[0]. long,但相反,您正在做arr[0]. long和arr[1]。长度,如果数组不是正方形,则会两次获得相同的维度并导致错误。

我还允许向任何方向移动,通过使用预期的路径来防止再次重新检查同一节点。这可能是一个布尔数组。抱歉,如果我的x/y递归看起来很粗糙。。。我真的更喜欢环或。forEach或=

可以使用可选参数清理-1,0,而不是在第一次遍历时进行迭代。

如果您可能发现任何错误或边缘情况,请告诉我。

 类似资料:
  • 问题内容: 基本上我有一个类似于以下问题: 有一个以2D正方形阵列表示的草莓植物花园。每棵植物(每个元素)都有许多草莓。您从数组的左上角开始,并且只能向右或向下移动。我需要设计一种递归方法来计算通过花园的路径,然后输出产量最高的草莓。 我认为我对非常简单的递归问题有所了解,但是这个问题已经超出了我的范围。我真的不确定创建递归方法的起点或终点。 非常感谢与代码相关的任何帮助或帮助我理解此问题背后的概

  • 这里, S=起点(2,2) B=块 O=打开 X=出口 我想做一个迷宫,可以检查北部,西部,东部和南部。如果X在附近,它将返回程序。如果没有,则检查起点周围的任何“O”,并以递归方式传递新的起点。它没有办法去,“X”没有找到,它将回到原来的起点(2,2)并检查西部,东部和南部。 节目结束后,我得到了: 但是,我期望递归后的输出是: 这是我现在的代码: startX和startY是起点的索引。 我不

  • 我们将如何测试数组中每个子数组的长度等于子数组元素之和的P倍的所有子数组组合。 一个简短的示例:编辑: 期望的结果: 长度=2,P*元素之和=1。子序列是 编辑约束: 这些问题属于什么样的问题集(例如:NP-hard?)?语言:C#

  • 我正在尝试了解如何使用动态编程解决在网格中查找所有唯一路径的问题: 机器人位于m x n网格的左上角(下图中标记为“开始”)。机器人只能在任何时间点向下或向右移动。机器人正试图到达网格的右下角(下图中标记为“Finish”)。有多少种可能的独特路径? 我正在看这篇文章,我想知道为什么在下面的解决方案中,矩阵被初始化为和,以及为什么在的函数签名中,最后一个参数被初始化为 然后在作者自下而上的解决方案

  • 我在JavaFX中创建了一个迷宫游戏,用户可以创建自己的迷宫并玩它。迷宫是使用带有CSS IDs的按钮构建的,CSS IDs取决于关卡临时存储的二维数组。 问题出现在项目的下一部分。我创建了一个生成随机迷宫的算法。为了使水平成为可能,我需要检查迷宫是否可解(即,你可以从起点(0,3)到终点(6,3))。 我使用相同的显示算法创建了一个单独的项目,类如下: 主要.java Runner.java M

  • 给定一个2d数组,我需要返回一个具有路径的矩阵,该路径递归地求和到给定的数字。 路径矩阵应为零,但总计为给定数字的路径除外,该路径将标记为1。 路径只能在 我尝试过所有的可能性,首先检查我是否已经去过下一个街区。 问题是在一些迭代之后,它会停止,并且不会返回并再次将块清除为0。 给定 在通话中 我以为算法会回来 我得到 相反 调用paintPath(mat1400,path,0,0);我想 或 问