计算01矩阵中的0Group的数量 二维数组表示

本文介绍了一种使用深度优先搜索(DFS)算法解决特定矩阵中独立0群数量问题的方法,并提供了完整的C语言实现代码。

题目源自于待字闺中的微信。

题目:给定一个n*n的board里面是0或1算出里面独立的0group的数量。比如

0 0 1 1 1
0 1 1 1 0
1 1 1 1 0
1 0 1 1 1
1 1 1 1 1

答案:3。


思路:虽然不是图,但是我仍然可以用图的DFS思想。我更没有必要用实现它对应的图。为了计数同时为了节省空间,把矩阵的元素本身来作为DFS时使用的标记量visited[ ]。


代码:

#include <stdio.h>
#include <malloc.h>
const int row = 5, col = 5;
//图的DFS,把所有连通结点标记为count
void DFS(int m[][col], int i, int j, int row, int col, int count)
{
	m[i][j] = count;
	if(i>0 && m[i-1][j] == 0)
	{
		DFS(m, i-1, j, row, col, count);
	}
	if(j>0 && m[i][j-1] == 0)
	{
		DFS(m, i, j-1, row, col, count);
	}
	if(i<row-1 && m[i+1][j] == 0)
	{
		DFS(m, i+1, j, row, col, count);
	}
	if(j<col-1 && m[i][j+1] == 0)
	{
		DFS(m, i, j+1, row, col, count);
	}
}

//对每个"为0且没有被标记"的结点进行DFS
int get_group(int m[][col],  int row, int col)
{
  int count = 1; //01都被占用了,所以从2起始吧
  for(int i=0;i<row;i++)
  {
    for(int j=0;j<col;j++)
    {
      if(m[i][j] == 0) 
	  {
		count++;
		DFS(m, i, j, row, col, count);  
	  }
    }
  }
  return count-1;//我是从2起始的
}

void display(int m[][5])
{
	for(int i=0;i<row;i++)
	{
		for(int j=0;j<col;j++)
			printf("%d ", m[i][j]);
		printf("\n");
	}

}
int main()
{
#if 0
  //手工输入矩阵的方式
  int (*m)[col] = (int (*)[col])malloc(sizeof(int)*row*col);
  for(int i=0;i<row;i++)
	  for(int j=0;j<col;j++)
		  scanf("%d",&m[i][j]);
#endif

#if 1
  //二维数组初始化的方式
  int m[][col] = {{0,0,1,1,1},
                  {0,1,1,1,0},
                  {1,1,0,1,0},
                  {1,0,1,0,0},
                  {1,0,0,0,1}};
#endif

  display(m);
  printf("%d\n", get_group(m, row, col));
  display(m);
  return 1;
}


学习:

1、这里学习一下c语言如何静态和动态实现二维数组,如何将二维数组作为函数参数。

2、学习一下DFS思想的使用。

### C语言中的一维数组与二维数组 #### 一维数组的定义和用法 在一维数组方面,C语言允许通过指定数据类型、数组名以及所需元素的数量来创建数组。例如: ```c int array[5]; // 创建一个包含五个整数类型的数组 ``` 初始化可以在声明的同时完成,也可以在之后逐个赋值。 ```c // 初始化时赋值 int array[] = {10, 20, 30, 40, 50}; // 或者单独给每个位置上的变量赋值 array[0] = 1; array[1] = 2; ... ``` 对于遍历和操作这些数值,则可以通过for循环实现[^1]。 #### 二维数组的定义和用法 关于二维数组,在C语言里同样遵循类似的模式——先说明存储的数据种类(比如`int`),接着给出名字加上方括号内的维度大小描述;如果要立即填充初始值的话,还可以采用大括号包裹的形式来进行多层嵌套表示矩阵结构。 ```c // 定义并初始化一个3×4的整形二维数组 int matrix[3][4] = { {1, 2, 3, 4}, {5, 6, 7, 8}, {9, 10, 11, 12} }; ``` 当需要引用某个特定的位置时,只需提供相应的行索引和列索引即可访到该处的内容。而针对整个表单的操作则往往借助双重循环达成目的。 ```c #include <stdio.h> void printMatrix(int mat[][4], int rows){ for (int i=0;i<rows;++i){ for (int j=0;j<4;++j){ printf("%d ",mat[i][j]); } putchar('\n'); } } int main(){ int myMat[3][4]={ {1,2,3,4},{5,6,7,8},{9,10,11,12} }; printMatrix(myMat,sizeof(myMat)/sizeof(myMat[0])); return 0; } ``` 上述例子展示了如何打印出一个已知尺寸的二维数组中的所有元素。 --- ### JavaScript 中的一维数组与二维数组 #### 一维数组的定义和用法 JavaScript 的一维数组非常灵活,既支持静态分配也兼容动态增长的方式构建列表对象。下面是一些基本的例子展示了一维数组的不同创建途径及其简单应用[^2]。 ```javascript let fruits = ['apple', 'banana']; // 字符串型数组 console.log(fruits.length); // 输出长度为2 fruits.push('orange'); // 添加新成员至末端 console.log(fruits.pop()); // 移除最后一个元素并返回它 ("orange") // 迭代处理每一个项目 fruits.forEach((item,index)=>{ console.log(`${index}:${item}`); }); ``` #### 二维数组的定义和用法 至于二维数组,在JS里面通常是以数组内含其他数组的方式来呈现表格化布局的信息集合体。这里有一个简单的实例用来解释这种概念性的组织形式。 ```javascript const tableData=[ ["Name","Age"], ["Alice",23], ["Bob",30] ]; function displayTable(dataArray){ dataArray.map(row=>{ row.join("\t").split(',').forEach(cell=>document.write(`<td>${cell}</td>`)); document.write("<br>"); }); } displayTable(tableData); ``` 此代码片段会按照HTML表格样式渲染传入参数所携带的数据集。 --- ### Python 中的一维数组与二维数组 Python虽然没有原生的一维或多维数组类型,但是可以利用列表(lists)轻松模拟这样的行为。特别是NumPy库提供了强大的ndarray类用于高效管理和运算大规模同质化的数字序列或网格状排列的对象群组。不过在这里仅讨论基础层面的知识点[^3]。 #### 列表作为一维数组 最直接的办法就是运用内置list容器去装载一系列相同性质的东西,就像这样: ```python oneDList=[1,'two',True,None] print(oneDList[-1]) # 访最后一位成员 None del oneDList[1:] # 删除除了第一个以外的所有项 print(oneDList) # 结果只剩余 [1] ``` #### 使用列表推导式生成二维数组 另外一种常见的做法是依靠列表解析表达式快速建立具有规律特征的矩形区域模型,如下所示: ```python # 构建一个由连续偶数组成的小规模方形阵列 squareOfEvens=[[x*2+y*2 for y in range(3)] for x in range(3)] print(squareOfEvens) # 提取第二行部成分 secondRow=squareOfEvens[1][:]; print(secondRow) ``` 需要注意的是,不同于某些编程环境下的切片机制,标准Python列表并不接受冒号前后的逗号分隔坐标轴指示器来做跨维度选取动作,这也就是为什么尝试执行类似于 `group[:,1]` 的语句会导致错误提示的原因所在。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值