我是初学者编写者并编写了
代码询问用户的姓名
检查长度是否> 15,如果是,它将要求用户在重新启动程序时输入更短的名称
如果长度有效,则大写输入名称的第一个字母
显示类似"嗨名称"
然而,无论我输入什么,程序都会一直存在。这是我做的:
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <conio.h>
int main(void)
{
char str_name[15];
printf("Please enter your first name to begin: ");
scanf_s("%14s", str_name, _countof(str_name));
getchar();
if (strlen(str_name) > 15)
{
printf("The entered name is too long, please restart the program and try again.");
getchar();
exit(0);
}
else
{
str_name[0] = toupper(str_name[0]);
printf("Hi %s.\n", str_name);
getchar();
}
return 0;
}
答案 0 :(得分:1)
您只需使用fgets()
即可读取输入缓冲区。
"
从指定的流中读取一行并将其存储在 str 指向的缓冲区中。当读取char *fgets(char *str, int n, FILE *stream)
个字符,读取换行符或达到n-1
时,它会停止。
有关EOF
的一些注意事项:
fgets()
。 NULL
个字符。可以替换为\n
。\0
或stdin
个对象中读取。以下是一些示例代码:
FILE
答案 1 :(得分:0)
您的代码中存在以下几个问题:
缓冲区大小太短:scanf()
不会将超过14个字节读入str_name
,因此无法测试用户是否输入了超过15个字符的名称。
toupper()
不应该被赋予char
参数,因为它仅针对类型unsigned char
和特殊值EOF
的值进行定义。将char
投射为unsigned char
。
您在终端窗口关闭之前暂停的尝试在Windows的长名称上失败,因为用户输入的额外字符在scanf_s()
之后仍然未决。 getchar()
读取一个并立即返回,程序退出并终止窗口关闭。打开终端窗口并手动运行程序,使其不会自动关闭。使用此方法,您可以删除getchar()
并使程序更具可移植性。
以下是更正后的版本:
#include <ctype.h>
#include <stdio.h>
int main(void) {
char str_name[17];
printf("Please enter your first name to begin: ");
if (scanf_s("%16s", str_name, sizeof(str_name))) {
printf("Premature end of file.\n");
return 1;
}
if (strlen(str_name) > 15) {
printf("The entered name is too long, please restart the program and try again.");
return 1;
}
str_name[0] = toupper((unsigned char)str_name[0]);
printf("Hi %s\n", str_name);
return 0;
}
答案 2 :(得分:-1)
问题是:
char Name[1]; // Declare a single element array.
Name[0] = toupper(str_name[0]); // Set it to the upper-case first letter.
// Try and print the nul-terminated string in Name - but there is no
// trailing zero (and the rest of the name is missing).
printf("Hi %s.\n", Name);
您需要的是:
str_name[0] = toupper(str_name[0]);
printf("Hi %s.\n", str_name);
另一个问题是str_name[0]
是char
值,而char可能会被签名。例如,如果您使用的是Windows-1252,则Ä
为196,或者作为签名字符,-60。 toupper
需要int
,必须为正¹。当-60作为signed char转换为int时,您将得到-60,并且超出范围错误。你需要把它写成:
str_name[0] = toupper((unsigned char)str_name[0]);
printf("Hi %s.\n", str_name);
(对不起。)
¹Chrqlie指出要求实际上是参数必须是unsigned char
的值之一(根据定义 - 非负)或EOF(是< / em>否定)“
答案 3 :(得分:-1)
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
int main(void)
{
char str_name[16] = {0};
size_t len = 0;
int ch;
printf("Please enter your first name to begin: ");
while ((EOF != (ch = fgetc(stdin))) && (ch != '\n') && (len<sizeof(str_name)))
{
if (isalpha(ch))
{
str_name[len++] = ch;
}
}
if (len==sizeof(str_name))
{
fprintf(stderr, "Name too long\n");
}
else
{
str_name[len] = '\0';
printf ("Hi %c%s.\n", toupper(str_name[0]), &str_name[1]);
}
return 0;
}
如您所见,我更改了输入抓取功能。要检查输入str len,您应该读取每字节的字节数,而不是整个字符串:fgetc执行此操作。使用格式说明符如%14s
的scanf,它将返回一个修剪后的字符串,并且您无法警告用户有太长的名称。
另一点是检查插入的字符是字母而不是其他类型的字符:isalpha完成工作。
此外,c-string由chars加上一个空终止符('\ 0',0x00)组成,因此:15个字符串需要一个16字节的数组。
最后,您编写的第一个字母大写的代码是完全错误的:您传递的是打印1个char数组而不是c字符串。我的解决方案是其中之一。