我想打印我的结构数组但是我一直在分段错误, 我究竟做错了什么?我首先使用另一个函数来读入数据。然后我想能够查看我刚输入的内容。
#include <stdio.h>
#define max 100
#define min 30
struct vara{
char namn[min];
int saldo;
int nummer;
};
struct vara varor[max];
int addvara(struct vara varor[], int length)
{
int s, n = 1;
//char nm;
printf("Vill du scanna in vara? 1 för ja. 0 för att återgå till menyn\n");
scanf("%d", &n);
while(n != 0)
{
for(int i=0; i<length; i++)
{
printf("Namm, saldo, varunummer\n");
scanf("%s", varor[i].namn);
scanf("%d", &varor[i].saldo);
scanf("%d", &varor[i].nummer);
//struct vara invara = {"%s, %d, %d", nm, s, n};
//varor[length] = invara;
i=length;
length++;
printf("Vill du scanna in vara? 1 för ja. 0 för att återgå till menyn\n");
scanf("%d", &n);
}
}
return length;
}
void view(struct vara varor[], int length)
{
printf("Varunummer \t\t Namn \t\t Varunummer\n");
for(int i=0; i<length; i++)
{
printf("%s \t\t %d \t\t %d", varor[i].namn, varor[i].saldo, varor[i].nummer);
}
}
答案 0 :(得分:3)
我认为问题的根源是你的addvara
函数,你的循环没有意义。
使用i=length;
覆盖正在运行的索引,然后执行
length++;
。如果用户希望继续,则退出for
循环并输入它
再次,根据用户输入值的次数,你是
最终访问varor
越界,这是未定义的行为
并且这是一个分段错误。
我会像这样重写addvara
函数:
// helper function to clean stdin
void clean_stdin()
{
int c;
while((c = getchar()) != '\n' && c != EOF);
}
// helper function to read in a loop until you get the value
// return 1 on success, 0 on failure, cannot continue reading
int read_from_stdin(const char *format, void *ptr, const char *prompt)
{
int err;
do {
if(prompt)
{
printf("%s", prompt);
fflush(stdout);
}
err = scanf(format, ptr);
if(err == EOF)
return 0;
if(err != 1)
{
printf("Invalid value, try again\n");
clean_stdin();
}
} while(err != 1);
return 1;
}
int addvara(struct vara varor[], int length)
{
if(varor == NULL)
return -1; // error value
if(length < 0)
return -1;
// helper to creata a format for scanf
// %29[^\n]s, the number depends on sizeof varor[0].namn
char strfmt[100];
sprintf(strfmt, "%%%zu[^\n]s", sizeof(varor[0].namn) - 1);
int i;
for(i = 0; i < length; ++i)
{
int ask;
if(read_from_stdin("%d", &ask, "Vill du scanna in vara? 1 för ja. 0 för att återgå till menyn\n") == 0)
{
fprintf(stderr, "cannot continue reading\n");
return i; // number of values added so far
}
if(ask == 0)
return i; // the number of values added
// otherwise scanf might complain about leftovers in the input buffer
clean_stdin();
if(read_from_stdin(strfmt, varor[i].namn, "Namm: ") == 0)
{
fprintf(stderr, "cannot continue reading\n");
return i; // number of values added so far
}
// otherwise scanf might complain about leftovers in the input buffer
clean_stdin();
if(read_from_stdin("%d", &varor[i].saldo, "Saldo: ") == 0)
{
fprintf(stderr, "cannot continue reading\n");
return i; // number of values added so far
}
if(read_from_stdin("%d", &varor[i].nummer, "Varunummer: ") == 0)
{
fprintf(stderr, "cannot continue reading\n");
return i; // number of values added so far
}
putchar('\n');
}
return i;
}
您的打印功能看起来不错。但是你可以改善你的格式 输出,例如:
void view(struct vara varor[], int length)
{
printf("%-30s %-10s %s\n", "Namn", "Saldo", "Nummer");
for(int i=0; i<length; i++)
printf("%-30s %-10d %d\n", varor[i].namn, varor[i].saldo, varor[i].nummer);
}
输出看起来像这样
Namn Saldo Nummer
Jan 129 1113232
Maria 232 44342234
修改强>
正如chux在评论中指出的那样,我的read_from_stdin
函数具有技术性
未定义的bevahiour,因为scanf
需要int*
指针%d
格式,我正在使用void*
指针。
我想在这里引用chux:
chux在comments
中写道
"%d"
需要int *
,而不是void *
。void *
和int*
可以具有不同的宽度,编码
然而,在编写C代码15年后,我从来没有遇到过这种情况的常用架构 像这样的函数实际上会失败。除非您的目标架构不是异国情调,否则此功能将按照我的意图运行。