我使用了一个原始代码片段进行测试。原始形式如下:
#include <stdio.h>
#include <stdlib.h>
int main() {
int i,j;
int size_x = 100;
int size_y = 100;
int size_z = 100;
double ***x;
x = malloc(size_y * sizeof(*x));
for (i = 0; i < size_y; i++)
x[i] = malloc(size_x * sizeof(**x));
for (j = 0; j < size_x; j++)
x[i][j] = malloc(size_z * sizeof(***x));
return 0;
}
在执行时,我得到了一个Segmentation error
,我不知道这个错误可能来自哪里。
此错误的原因是什么? i
索引等于第一个循环后的size_y-1
,第二个循环似乎是正确的......
gdb
给予backtrace
:
Program received signal SIGSEGV, Segmentation fault.
0x00000000004005b6 in main () at main_Syntax_Alloc_SEGFAULT.c:17
17 x[i][j] = malloc(size_z * sizeof(***x));
从那以后,我已经纠正了这个代码片段以获得正确的分配,通过执行以下操作:
double ***x;
x = malloc(size_y * sizeof(*x));
for (i = 0; i < size_y; i++)
{
x[i] = malloc(size_x * sizeof(**x));
for (j = 0; j < size_x; j++)
x[i][j] = malloc(size_z * sizeof(***x));
}
但是我想知道上面代码段的第一个版本的分段错误的起源。
i
索引等于第一次循环后的size_y-1
不,不是。如果是的话,循环还没有结束。
循环后
for (i = 0; i < size_y; i++)
i
的值不是<size_y
.有了这个,这条线
x[i][j] = ...
访问无效内存,调用未定义的行为。从那以后,任何事情都可能发生。
循环后的简单printf()
i
就可以证明这一点。
顺便说一句,所有这些int
都应该是size_t
s。