这似乎是在最后%s
的printf
完全被跳过。
这是整个代码:
#include <stdio.h>
int main(void){
char address[100];
char city[100];
char state[2];
char zip[15];
printf("Enter street address: ");
scanf(" %[^\n]",&address);
printf("Enter city: ");
scanf(" %[^\n]",&city);
printf("Enter state: ");
scanf(" %s",&state);
printf("Enter ZIP Code: ");
scanf(" %s",&zip);
printf("%s\n%s, %s %s",address,city,state,zip);
return 0;
}
当输入该地址:
1 Main Street New York City, NY 12345
该程序打印:
1 Main Street , NY 12345
我想不通这个问题的原因。 任何帮助将不胜感激,因为我的想法。
#include <stdio.h>
int main(void){
char address[100];
char city[100];
char state[2];
char zip[15];
printf("Enter street address: ");
scanf(" %[^\n]",&address);
printf("Enter city: ");
scanf(" %[^\n]",&city);
printf("Enter state: ");
scanf(" %s",&state);
printf("Enter ZIP Code: ");
scanf(" %s",&zip);
printf("\nONE: %s\n",address);
printf("TWO: %s\n",city);
printf("THREE: %s\n",state);
printf("FOUR: %s\n",zip);
return 0;
}
复制粘贴到https://www.codechef.com/ide,你会看到下面的输出:
Enter street address: Enter city: Enter state: Enter ZIP Code:
ONE: 1 Main Street
TWO: New York City, NY 12345
THREE:
FOUR: @
您存储而不是在逗号停止在城市的一切。你觉得你的城市scanf函数是干什么的?
后续的代码是我的工作站上运行良好。
#include <stdio.h>
int main(void){
char address[100];
char city[100];
char state[2];
char zip[15];
printf("Enter street address: ");
scanf(" %[^\n]",address);
printf("Enter city: ");
scanf(" %[^\n]",city);
printf("Enter state: ");
scanf(" %s",state);
printf("Enter ZIP Code: ");
scanf(" %s",zip);
printf("%s\n%s, %s %s",address,city,state,zip);
return 0;
}
正如评论和其他答案提到的,你有许多问题。前两个可以立即激活未定义行为是:
"NY"
作为一个字符串到char state[2];
。为了在C有效的字符串,字符必须由一个NUL终止字符终止。这意味着存储2个字符的状态缩写,你需要存储(最小)的3个字符。例如。 {'N', 'Y', '\0'}
。 (主@JonathanLeffler推导出state
短存储的直接后果如何可能导致'\0'
字符将被存储为在city
的第一个字符造成city
是一个空字符串);scanf
你必须提供一个指向足够的存储你正在阅读的串串。由于address, city, state, zip
是字符数组,上访问,它们被转换的指针的第一个字符(参见:C11 Standard - 6.3.2.1 Other Operands - Lvalues, arrays, and function designators(p3))所以作为scanf
一个参数,并没有'&'
使用时每个已经是一个指针(地址)操作者需要在它们前面参数列表。其他注意事项,避免在您的代码,除非绝对必要使用魔法数字。 100, 2, 15
低于魔法数字。
char address[100];
char city[100];
char state[2];
char zip[15];
如果您需要在address, city, state, zip
字符数恒定,#define
为每个或使用全局enum
做同样的事情,例如
enum { STSZ = 3, ZIPSZ = 15, CIADDR = 100 }; /* constants */
(注city
和address
都是100
,所以单CIADDR
常数都行)
当数绝对在你的代码需要?与scanf
系列函数读取时,如果提供了一个场宽度调节器,以保护您的数组边界。另外,使用scanf
家庭时,必须检查返回,每一次。否则,匹配或输入故障,可能会发生(或用户可以生成一个手动EOF
取消输入),你盲目地推进使用未填充可能留下不确定调用未定义行为变量。
把这些拼在一起,并思考着,你可能只是发现自己处理代码中的1个多地址,以下是可以在单个文本行读city, state zip
值的示例和值存储在一个结构。 (这允许你声明结构的阵列,或一个指针,并根据需要与一个以上的地址以后处理时分配)
#include <stdio.h>
enum { STSZ = 3, ZIPSZ = 15, CIADDR = 100 }; /* constants */
typedef struct { /* simple struct presuming in the future */
char address[CIADDR], /* you may have more than 1 address */
city[CIADDR],
state[STSZ], /* STSZ must be 3 to read a string of 2-char */
zip[ZIPSZ];
} loc_t;
int main (void) {
loc_t location1 = { .address = "" }; /* declare/initialize struct */
printf ("enter street address: "); /* prompt/read/validate address */
if (scanf (" %99[^\n]", location1.address) != 1) {
fputs ("sscanf() error: invalid address.\n", stderr);
return 1;
}
printf ("enter city: "); /* prompt/read/validate city */
if (scanf (" %99[^,],", location1.city) != 1) {
fputs ("sscanf() error: invalid city.\n", stderr);
return 1;
}
printf ("enter state: "); /* prompt/read/validate state */
if (scanf (" %2s", location1.state) != 1) {
fputs ("sscanf() error: invalid state.\n", stderr);
return 1;
}
printf ("enter zip: "); /* prompt/read/validate zip */
if (scanf (" %14s,", location1.zip) != 1) {
fputs ("sscanf() error: invalid zip.\n", stderr);
return 1;
}
/* output results preceeded by 2-newlines */
printf ("\n\n%s\n%s, %s %s\n", location1.address, location1.city,
location1.state, location1.zip);
}
(注意:数字为场宽度改性剂包括在每个scanf
调用保护你的数组边界另外多个'\n'
输出补偿了未使用的提示之前时city, state zip
是所有在"city: "
提示输入。)
实施例使用/输出
进入"New York City, NY 12345"
截至"enter city: "
提示一个字符串:
$ ./bin/readaddr
enter street address: 1 Main Street
enter city: New York City, NY 12345
enter state: enter zip:
1 Main Street
New York City, NY 12345
在寻找的东西,让我知道,如果你还有其他问题。