我正在编写一个小型c程序来练习malloc
和sscanf
库函数。但不幸的是我得到了分段错误错误。我用Google搜索并挣扎了好几个小时但没有结果。任何人都可以引导我走出这个?
#include <stdio.h>
#include <stdlib.h>
void print_array(int a[], int num_elements);
int main(void) {
int m;
printf("How many numbers do you count: \n");
scanf("%d", &m);
int *a = (int*)malloc(m * sizeof(int*));
char buf[100];
setbuf(stdin, NULL);
if (fgets(buf, sizeof buf, stdin) != NULL) {
char *p = buf;
int n, index;
while (sscanf(p, "%d %n", &a[index], &n) == 1 && index < m) {
// do something with array[i]
index++; // Increment after success @BLUEPIXY
p += n;
}
if (*p != '\0')
printf("you are giving non-numbers, will be ignored");
}
print_array(a, m);
free(a);
return 0;
}
void print_array(int a[], int num_elements) {
int i;
for (i = 0; i < num_elements; i++) {
printf("%d ", a[i]);
}
}
答案 0 :(得分:3)
您的malloc
有问题。将int* a = (int*)malloc(m*sizeof(int*));
替换为int* a = (int *)malloc(m*sizeof(int));
。
你很幸运,sizeof
int
小于int*
,否则你可能会遇到很多问题。
我无法重现错误,下次更好地提供输入文本,但调试segfault我依赖于gdb。
$ gcc -g prog.c -o prog
$ gdb prog
GDB&GT;运行[args]
这会破坏导致段错误的程序。使用本教程可获得更多知识。 gdb tutorial
答案 1 :(得分:1)
您的程序有多处错误:
您不检查scanf()
的返回值。输入无效会导致m
保持未初始化状态,分配m * sizeof(int)
可能会失败。
为malloc
计算的大小不正确。在C中不需要转换malloc()
的返回值,并将其视为错误的样式。此外,您应该检查分配失败。请改用:
int *a = malloc(m * sizeof(int));
index
在sscanf(p, "%d %n", &a[index], &n)
中未初始化,肯定会导致未定义的行为,因为您告诉sscanf()
将int
值存储到内存中的某个随机地址中。
您在存储到index < m
后测试&a[index]
,导致潜在的缓冲区溢出。在sscanf()
。
以下是修改后的版本:
#include <stdio.h>
#include <stdlib.h>
void print_array(const int a[], int num_elements);
int main(void) {
int m;
printf("How many numbers do you count:\n");
if (scanf("%d", &m) != 1 || m <= 0) {
fprintf(stderr, "invalid input\n");
return 1;
}
int *a = malloc(m * sizeof(int));
if (a == NULL) {
fprintf(stderr, "memory allocation failed\n");
return 1;
}
char buf[100];
setbuf(stdin, NULL); // why do you want stdin to be unbuffered?
if (fgets(buf, sizeof buf, stdin) != NULL) {
char *p = buf;
int n, index = 0;
while (index < m && sscanf(p, "%d %n", &a[index], &n) == 1) {
// do something with array[i]
index++; // Increment after success @BLUEPIXY
p += n;
}
if (*p != '\0') {
printf("you are giving non-numbers or extra input, will be ignored\n");
}
}
print_array(a, m);
free(a);
return 0;
}
void print_array(const int a[], int num_elements) {
for (int i = 0; i < num_elements; i++) {
printf("%d ", a[i]);
}
printf("\n");
}
答案 2 :(得分:0)
大多数[潜在]错误原因似乎来自未初始化自动变量:
scanf("%d",&m);
如果失败,那么m
有一个未定义的值,因为你没有初始化它。
sscanf
中的{p>您使用&a[index]
,但index
尚未初始化,因此可以在任何地方写入。
另请参阅注释,以识别更多错误(例如,检查sscanf
的返回值)。