为什么会出现seg故障(多维数组C)

为什么会出现seg故障(多维数组C),c,arrays,multidimensional-array,segmentation-fault,C,Arrays,Multidimensional Array,Segmentation Fault,我似乎不知道我做错了什么 int main(int argc, char **argv) { int height = 4, width = 6; int **map; map = (int **)(malloc(height * sizeof(int*))); for(i = 0; i < height; i++) { map[i] = (int *)(malloc(width * sizeof(int))); } fill_map(&map, h

我似乎不知道我做错了什么

int main(int argc, char **argv) {
  int height = 4, width = 6;
  int **map;
  map = (int **)(malloc(height * sizeof(int*)));
  for(i = 0; i < height; i++) {
    map[i] = (int *)(malloc(width * sizeof(int)));
  }
  fill_map(&map, height, width);
}

void fill_map(int ***map, int height, int width) {
  int i, k, character;
  for(i = 0; i < height; i++) {
    k = 0;
    while((character = getchar()) != '\n') {
        *map[i][k] = character;
        k++;
    }
  }
}
int main(int argc,char**argv){
内部高度=4,宽度=6;
国际**地图;
地图=(int**)(malloc(高度*尺寸)(int*);
对于(i=0;i

我在内部while循环中的fill_map中得到一个segfault,为什么?

不发送&映射到函数,将原型更改为接收(int**map)或使用(*map)[I][k]。这是因为间接运算符*的优先级低于[]运算符。

不要向函数发送和映射,将原型更改为接收(int**map)或使用(*map)[i][k]。这是因为间接运算符*的优先级低于[]运算符。

如何结束while循环,是否在数组中保留了“\n”符号?您刚刚分配了内存并尝试在其上运行。它永远找不到“\n”,因此while循环超出内存位置,您会得到分段错误。

您希望如何结束while循环,您是否在阵列中保留过“\n”im?您刚刚分配了内存并尝试在其上运行。它永远找不到“\n”,因此当循环离开内存位置时,就会出现分段错误。

我会使用gdb或其他调试器。用调试符号编译程序,在那里运行,它会告诉您正在进行分段错误处理的行。

我会使用gdb或其他调试器。使用调试符号编译程序,在其中运行,它将告诉您正在进行分段的行。

首先,请注意“prmg”和“perreal”给出的建议

不要强制转换malloc的返回值。malloc返回一个void*,不需要强制转换。如果你忘了把
#包括在内,那你就是在自找麻烦

map = malloc( height * sizeof *map );
首先——听取“prmg”和“perreal”的建议

不要强制转换malloc的返回值。malloc返回一个void*,不需要强制转换。如果你忘了把#包括在内,那你就是在自找麻烦

map = malloc( height * sizeof *map );

您的分段错误是由于您错误地取消了对
map
的引用;你应该把它写成
(*map)[i][k]
,而不是
*map[i][k]
。尽管最好在调用
填充映射
时取消
&
,并相应地调整原型:

fill_map(map, height, width);
...
void fill_map(int **map, int height, int width)
{
  ...
  map[i][k] = character;
  ...
}
您可以像这样清理
malloc
调用:

map = malloc(height * sizeof *map);

在C1中不需要强制转换,这被认为是不好的做法



1这在C++中是不正确的;需要一个强制转换,但是如果您正在编写C++,则应该使用<代码>新< /COD>而不是<代码> MalOC/。p> 您的分段错误来自于您错误地取消对
map
的引用;你应该把它写成
(*map)[i][k]
,而不是
*map[i][k]
。尽管最好在调用
填充映射
时取消
&
,并相应地调整原型:

fill_map(map, height, width);
...
void fill_map(int **map, int height, int width)
{
  ...
  map[i][k] = character;
  ...
}
您可以像这样清理
malloc
调用:

map = malloc(height * sizeof *map);

在C1中不需要强制转换,这被认为是不好的做法



1这在C++中是不正确的;需要一个强制转换,但是如果您正在编写C++,则应该使用<代码>新< /COD>而不是<代码> MalOC/。p> 您使用的不是2D阵列,而是它的模拟。在现代C语言中,从C99开始,使用“可变修改类型”,您的任务非常简单:

#include <stddef.h>
#include <stdlib.h>
#include <stdio.h>

void fill_map(size_t height, size_t width, char map[height][width]) {
  int character;
  for(size_t i = 0; i < height; i++) {
    for (size_t k = 0; k < width; k++) {
      if ((character = getchar()) != '\n')
        map[i][k] = character;
      else break;
    }
  }
}

int main(int argc, char **argv) {
  size_t height = 4, width = 6;
  char (*map)[width] = malloc(sizeof(char[height][width]));
  fill_map(height, width, map);
}
#包括
#包括
#包括
空白填充图(大小高度、大小宽度、字符图[高度][宽度]){
整数字符;
对于(尺寸i=0;i<高度;i++){
对于(大小k=0;k
  • 首先传递矩阵维度,然后可以在矩阵参数的声明中简单地使用它们
  • 使用
    size\u t
    编制索引
  • 不要投马洛克的回归
  • 注意循环的边界
  • 最好检查文件的结尾(家庭作业)

您使用的不是2D阵列,而是它的模拟。在现代C语言中,从C99开始,使用“可变修改类型”,您的任务非常简单:

#include <stddef.h>
#include <stdlib.h>
#include <stdio.h>

void fill_map(size_t height, size_t width, char map[height][width]) {
  int character;
  for(size_t i = 0; i < height; i++) {
    for (size_t k = 0; k < width; k++) {
      if ((character = getchar()) != '\n')
        map[i][k] = character;
      else break;
    }
  }
}

int main(int argc, char **argv) {
  size_t height = 4, width = 6;
  char (*map)[width] = malloc(sizeof(char[height][width]));
  fill_map(height, width, map);
}
#包括
#包括
#包括
空白填充图(大小高度、大小宽度、字符图[高度][宽度]){
整数字符;
对于(尺寸i=0;i<高度;i++){
对于(大小k=0;k
  • 首先传递矩阵维度,然后可以在矩阵参数的声明中简单地使用它们
  • 使用
    size\u t
    编制索引
  • 不要投马洛克的回归
  • 注意循环的边界
  • 最好检查文件的结尾(家庭作业)

提高编译器的警告级别,注意警告!编译器警告对这个问题没有多大帮助-我没有从GCC和
-Wall-Wextra
中得到有用的警告,也没有从MSVC和
-Wall-W4
中得到有用的警告。提高编译器的警告级别,注意警告!编译器警告对这个问题没有多大帮助-我没有从GCC和
-Wall-Wextra
中得到有用的警告,或者从MSVC和
-Wall-W4
中得到有用的警告