【问题标题】:c - Checking for null in a 2d arrayc - 检查二维数组中的空值
【发布时间】:2017-02-10 21:22:08
【问题描述】:

我正在从输入文件中填充 10 x 10 的字符网格。 我需要检查网格是否是正方形(即有 N x N 个字符,其中 N

输入文件是这样的:

pitk
olpe
pkey
tope

当我在 gdb 中打印网格时,我得到以下结果:

$1 = {"pitk\000\000\000\000\366h", 
      "olpe\000\000\001\000\000", 
      "pkey\000\000\000\000\000", 
      "tope\000\000\000\000\000", 
      "\000\344\241\367\377\177\000\000", <incomplete sequence \336>, 
      "\000\377\377\177\000\000\037\355\336", <incomplete sequence \367>, 
      "\000\177\000\000\000\000\000\000\000", 
      "\000\000\000\000\000\000\000\000\000", 
      "\000\000\000\000\000\000\000\000\r\020", 
      "\000\000\000\000\000\000\000\000\000"}

我检查网格是否有效的主要功能部分是:

  bool check = (checknxn(grid));
  if(check == false) {
    fprintf(stderr, "Invalid Input!\n");
    exit(0);
  }

checknxn 函数:

bool checknxn(char grid[10][10]) {
  int columns = 0;
  for(int i=0;i<10;i++) {
    if(grid[0][i]!=NULL)
      columns++;
    else {
      break;
    }
  }

  for(int i=1;i<10;i++) {
    for(int j=columns;j<10;j++) {
    if(grid[i][j]!=NULL)
      return false;
    }
  }

  int rows = 0;
  for(int i=0;i<10;i++) {
    if(grid[i][0]!=NULL)
      rows++;
    else {
      break;
    }
  }
  if (!(rows == columns))
    return false;
  for(int i=0;i<rows;i++) {
    for(int j=0;j<columns;j++) {
      if(grid[i][j]==NULL) {
        return false;
      }
    }
  }
  return true;
}

这将返回 false,并且我的程序退出,即使在这种情况下输入网格是有效的。

我无法弄清楚为什么 checknxn 函数在这种情况下返回 false。

更新:这就是我初始化网格的方式:

FILE *file1 = fopen(argv[1], "r"); // "r" for read

  char grid[10][10];

  char c;
  for(int i=0;i<10;i++){
    for(int j=0;j<10;j++){
      fscanf(file1,"%c", &c);
      if (c == '\n') {
        grid[i][j] = '\0';
        break;
      }
      if (c == ' ') {
        grid[i][j] = '\0';
        continue;
      }
      if (c == '\0') {
        grid[i][j] = '\0';
        continue;
      }
      else {
        grid[i][j] = c;
      }
    }
  }

【问题讨论】:

  • 你试过你的调试器(甚至是 printf 吗?)。鉴于您的输入,我可以看到它失败的原因。也许首先将`i`和j重命名为rowcol,以便更容易理解...
  • @John3136 我已经使用我的调试器来检查网格的值,但没有在 checknxn 函数上使用它,因为我不确定如何在辅助函数上使用 gdb。
  • 直接进入吧。
  • @John3136 我不知道该怎么做。你能给我指出一个可以提供帮助的资源吗?

标签: c arrays null grid boolean


【解决方案1】:

未初始化数据的经典 C 错误。 Memset 可能是要走的路(见下文)。

memset(grid, 0, sizeof(grid[0][0]) * rows * columns);

【讨论】:

    【解决方案2】:

    您的网格未完全初始化(您没有将每个单元格设置为例如:\0),因此您只有正确的字符串和每行的开头定义。当你这样做时,初始化网格,也就是说,你不检查单元格是NULL,因为它们不是指针而是实际内容,所以你检查例如:\0,如果你已经将网格初始化为那个价值。

    编辑在 OP 提供额外信息后

    要初始化该网格,您可以执行以下操作

    char grid[10][10];
    for(int i=0;i<10;i++){
      for(int j=0;j<10;j++){
        grid[i][1j] = '\0';
      }
    } 
    

    然后才进行填充。不要混用。

    如果要检查每个单元格是否被填满,即:不是\0

      for(int i=0;i<rows;i++) {
        for(int j=0;j<columns;j++) {
          if(grid[i][j] != `\0`) {
            return false;
          }
        }
      }
    

    但是您想在其中加载 C 字符串,并且 C 字符串以 \0 结尾。要么将字符串加载到不带尾随 \0 的单元格中,要么调整循环以检查到 row_length-2 而不是 row_length -1

    如果您有字符串,一种更简单的方法:测量每个 row 中的字符串长度,如果它们都相同并且行数对应于字符串长度,则您有一个方形网格。

    【讨论】:

    • 我尝试将我的网格初始化为 '\0' 而不是 NULL(请参阅上面的更新)和我的 checknxn 函数来检查它,但我仍然遇到同样的问题......
    猜你喜欢
    • 1970-01-01
    • 2014-02-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-01-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多