【发布时间】:2023-03-27 10:57:01
【问题描述】:
我目前正在尝试解决输入应如下所示的问题
int hours(int rows, int columns, List<List<Integer> > grid)
其中列表网格是 0 和 1 的矩阵(0 表示不完整,1 表示完整)如下:
0 1 1 0 1
0 1 0 1 0
0 0 0 0 1
0 1 0 0 0
每个值代表网络中的一台机器互相发送文件,因此如果值为“1”,则该节点能够将文件发送给所有邻居(对角线不计算在内)仅上/下/右/左)。问题是一旦 0 变为 1(受相邻单元的影响),它就无法在 1 小时之前将文件发送给任何其他邻居。
问题的目标是返回所有节点接收文件需要多少小时? (换句话说,所有的矩阵都变成了 1。考虑运行时间复杂度
为了直观的解释:(在第一个小时之后,这应该是矩阵的状态,被认为是一次迭代):
1 1 1 1 1
1 1 1 1 1
0 1 0 1 1
1 1 1 0 1
所以,我采用了一种方法,在矩阵中循环查看提供的网格并将值附加到临时数组中(因为我不知道如何更新或附加主列表中的列表值)。然后,一旦行索引达到最大值,我将 1 小时添加到 int 变量并将值添加到主网格。
我知道下面的代码还没有工作/完成,可能有语法错误,但你明白了这个想法和方法。
我的问题是,有没有比我的更简单有效的方法?我还找到了一个解决方案here,但如果我的想法值得的话,这只适用于二维数组。但是,这 4 个嵌套循环不会弄乱代码的复杂性吗?
List<List<Integer>> grid2 = grid1;
boolean received= false;
int hours=0;
int rows_Temp = 0 ;
int columsTemp = 0 ;
int[][] grid2 = null ;
while(rows_Temp<rows&&!received)
{
if(rows_Temp==rows-1)
{
rows_Temp=0;
}
if(rows_Temp==0)
{
//create an array with the grid dimention
grid2= new int[rows][columns];
}
//manage top left corner
if(rows_Temp==0 && columsTemp == 0 )
{
//find right & down
int center= grid.get(rows_Temp).get(columsTemp);
int right = grid.get(rows_Temp).get(columsTemp+1);
int down = grid.get(rows_Temp+1).get(columsTemp);
if(center==1)
{
if(right==0)
{
grid2[rows_Temp][columsTemp+1] = 1;
}
if(down==0)
{
grid2[rows_Temp+1][columsTemp]=1;
}
}
}
//manage top right corner
else if(rows_Temp==0 && columsTemp == columns-1)
{
//find left and down
int center= grid.get(rows_Temp).get(columsTemp);
int left = grid.get(rows_Temp).get(columsTemp-1);
int down = grid.get(rows_Temp+1).get(columsTemp);
if(center==1)
{
if(left==0)
{
grid2[rows_Temp][columsTemp-1] = 1;
}
if(down==0)
{
grid2[rows_Temp+1][columsTemp]=1;
}
}
}
//mange down left corner of the array
else if(rows_Temp==rows-1 && columsTemp == 0)
{
//find up and right
int center= grid.get(rows_Temp).get(columsTemp);
int right = grid.get(rows_Temp).get(columsTemp+1);
int up = grid.get(rows_Temp-1).get(columsTemp);
if(center==1)
{
if(right==0)
{
grid2[rows_Temp][columsTemp+1] = 1;
}
if(up==0)
{
grid2[rows_Temp-1][columsTemp]=1;
}
}
}
//manage down right corner
else if(rows_Temp==rows-1 && columsTemp == columns-1)
{
//find left and up
int center= grid.get(rows_Temp).get(columsTemp);
int left = grid.get(rows_Temp).get(columsTemp-1);
int up = grid.get(rows_Temp-1).get(columsTemp);
if(center==1)
{
if(left==0)
{
grid2[rows_Temp][columsTemp-1] = 1;
}
if(up==0)
{
grid2[rows_Temp-1][columsTemp]=1;
}
}
}
//manage left sides but not corners
else if(rows_Temp!=0&& rows_Temp!=rows-1&& columsTemp==0)
{
int center= grid.get(rows_Temp).get(columsTemp);
int right = grid.get(rows_Temp).get(columsTemp+1);
int up = grid.get(rows_Temp-1).get(columsTemp);
int down = grid.get(rows_Temp+1).get(columsTemp);
if(center==1)
{
if(right==0)
{
grid2[rows_Temp][columsTemp+1] = 1;
}
if(up==0)
{
grid2[rows_Temp-1][columsTemp]=1;
}
if(down==0)
{
grid2[rows_Temp+1][columsTemp]=1;
}
}
}
if(columsTemp==columns-1)
{
columsTemp=0;
rows_Temp++;
System.out.println();
}
else
{
columsTemp++;
}
}
System.out.println("------------");
return 0 ;
}
【问题讨论】:
-
根据你的例子,我认为对角线邻居不算数。
-
是的,只有上/下/右/左
-
您应该从最初的 1 开始进行广度优先搜索。遍历所有单元格所需的层数是填充矩阵的小时数。
-
好的,谢谢,我会搜索算法,但在那之前会检查周围的上/下/左右并能够将零更改为一吗??
-
不确定我是否告诉过你所陈述的问题......但我在问题中写的第二次迭代发生在第一个小时结束时......并且该典型测试用例的解决方案是2 小时,因为第三次迭代会将它们全部变成一个
标签: java algorithm data-structures runtime time-complexity