我正在构建一个程序,使用户能够输入电影并打印出用户输入的信息。
我正在使用struct
来定义电影的变量。问题是,当用户输入第一个带有空格的fscanf()
时。示例:“Miami Vice”所有其他puts()
相互打印。 stdin
之后无效。我不知道为什么会这样。
我一直在阅读关于gets()并且它有安全问题所以我应该使用fgets()或fscanf()来实现这一点。但我无法弄清楚这里的问题是什么。
的main.c
#include <stdio.h>
#include <stdlib.h>
#include "main.h"
int main()
{
struct movie m;
puts("What was the title of the movie you saw?");
fscanf(stdin, "%s", m.title);
puts("What was the relase year?");
fscanf(stdin, "%d", &m.year);
puts("How would you rate the movie? (1-10)");
fscanf(stdin, "%d", &m.rate);
printf("You saw the movie %s which was released %d and you rated it a %d", m.title, m.year, m.rate);
return 0;
}
main.h
struct movie {
char title[40];
int rate;
int year;
};
答案 0 :(得分:1)
每当读取字符串作为输入时,请尝试使用fgets()
。无论如何这里是我修改了一下的代码。您可以根据自己的需要修改代码。
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
struct movie {
char title[40];
int rate;
int year;
};
int main(){
struct movie m;
char *newline_char=NULL;
puts("What was the title of the movie you saw?");
fgets(m.title,40,stdin);
//The below two lines of code are used to remove the '\n'
//character from the input since fgets() also stores the '\n'
//character. Replace the '\n' char with '\0' character.
if((newline_char=strchr(m.title,'\n')) != NULL){
*newline_char = '\0';
}
puts("What was the relase year?");
fscanf(stdin, "%d", &m.year);
puts("How would you rate the movie? (1-10)");
fscanf(stdin, "%d", &m.rate);
printf("You saw the movie %s which was released %d and you rated it a %d", m.title, m.year, m.rate);
return 0;
}
正如chux建议的那样,您也可以只使用fgets()
并避免fscanf()
,如下面的代码所示,
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
struct movie {
char title[40];
int rate;
int year;
};
int main(){
struct movie m;
char *newline_char=NULL;
char input[256];
puts("What was the title of the movie you saw?");
fgets(m.title,40,stdin);
if((newline_char=strchr(m.title,'\n')) != NULL){
*newline_char = '\0';
}
puts("What was the relase year?");
fgets(input,256,stdin);
sscanf(input,"%d",&m.year);
puts("How would you rate the movie? (1-10)");
fgets(input,256,stdin);
sscanf(input,"%d",&m.rate);
printf("You saw the movie %s which was released %d and you rated it a %d", m.title, m.year, m.rate);
return 0;
}
答案 1 :(得分:0)
%s
格式指示scanf
读取单个字词。空格充当单词分隔符,因此只有Miami
被解析为m.title
并且Vice
保留在输入流中。对scanf
格式%d
的后续调用无法解析流中的整数并返回0
,导致m.year
和m.date
未初始化。因此,在最后一次调用printf
时打印其值时,会调用未定义的行为。
您可以使用其他格式更正问题:%[^\n]
。此外,您应该使用宽度说明符scanf
阻止m.title
在%39[^\n]
的末尾写入。如果在电影标题之前存在空格,则格式之前的其他将跳过空格。另外
%*c
会读取\n
,但不是必需的,因为后续的scanf("%d",...)
会跳过前导空格,包括输入流中待处理的\n
待处理空白。
以下是您的计划的修改版本:
#include <stdio.h>
#include <stdlib.h>
struct movie {
char title[40];
int rate;
int year;
};
int main(void) {
struct movie m;
puts("What was the title of the movie you saw?");
if (scanf(" %39[^\n]", m.title) != 1)
return 1;
puts("What was the release year?");
if (scanf("%d", &m.year) != 1)
return 1;
puts("How would you rate the movie? (1-10)");
if (scanf("%d", &m.rate) != 1)
return 1;
printf("You saw the movie %s which was released in %d and you rated it a %d\n",
m.title, m.year, m.rate);
return 0;
}