我正在制作一个课程代码,用于计算多达50个家庭成员的平均年龄,并显示居住在德克萨斯州的人的姓名。但每当我在Ideone上使用代码时,它给了我像“1098907648.000000”这样荒谬的数字,并且不显示任何德州人!我似乎无法理解什么是错的。我知道这是一个广泛的问题,但任何帮助将不胜感激!
// C code
// This program will calculate the average age of an inputted Family and display the number of members in texas.
#include <stdio.h>
#include <string.h>
/* Function for average age */
float average(float num1, int num2)
{
return num1/num2;
}
int main ()
{
const char texans;
char familymember[50];
char state, texas;
float avg, sum;
int age, members;
{
printf("Enter family member or type end to output data when finished. \n");
{
scanf("%s", familymember);
if (familymember != "end")
{
members = members + 1;
printf("Enter age \n");
scanf("%f", &age);
sum = sum + age;
printf("Enter state \n");
scanf("%s", &state);
if (state == "Texas")
{
strcpy(texans, familymember);
}
}
if (familymember == "end");
{
// fuction call
avg = average(sum, members);
printf("The average age of all family member's is %f and the number of family members currently residing in texas are %s\n", avg, texans);
}
}
}
return 0;
}
答案 0 :(得分:5)
此代码存在许多问题。
在C中,必须在使用其值之前初始化变量。与其他一些语言不同,变量 不 默认为零或任何此类值 - 它们以未定义状态开头。
在C中,将字符串与==
进行比较可能无法达到预期效果。这将检查两个字符指针是否指向同一位置。相反,您可能希望使用strcmp
,它接受两个字符串,如果相等则返回0
。
如果您希望后续;
开始)
的正文,请不要在if
{
之后加if
。如果包含分号,将始终执行'body',因为;
取代了正文。
您将scanf
字符串放入固定大小的缓冲区中。你没有防止溢出缓冲区的保护措施。这是一个安全漏洞,可能导致远程执行代码。
目前还不清楚你对strcpy(texans, familymember)
的意图,但几乎肯定是不对的。您可能打算将texans
int
初始化为0
并且当前有strcpy
,您可能需要使用++texans;
行。
......还有其他问题,正如其他人在评论中指出的那样。帮自己一个忙,自己编译代码。对于GCC-like,我推荐这些编译选项:
-std=c99 -Werror -Wall -Wextra -pedantic
这样做,我收到了这些错误:
/tmp/31642023.c:23:27: error: result of comparison against a string literal is
unspecified (use strncmp instead) [-Werror,-Wstring-compare]
if (familymember != "end")
^ ~~~~~
/tmp/31642023.c:27:25: error: format specifies type 'float *' but the argument
has type 'int *' [-Werror,-Wformat]
scanf("%f", &age);
~~ ^~~~
%d
/tmp/31642023.c:31:23: error: result of comparison against a string literal is
unspecified (use strncmp instead) [-Werror,-Wstring-compare]
if (state == "Texas")
^ ~~~~~~~
/tmp/31642023.c:31:23: error: comparison between pointer and integer
('int' and 'char *') [-Werror]
if (state == "Texas")
~~~~~ ^ ~~~~~~~
/tmp/31642023.c:33:22: error: incompatible integer to pointer conversion passing
'const char' to parameter of type 'const void *'
[-Werror,-Wint-conversion]
strcpy(texans, familymember);
^~~~~~
/tmp/31642023.c:33:22: error: incompatible integer to pointer conversion passing
'const char' to parameter of type 'const void *'
[-Werror,-Wint-conversion]
strcpy(texans, familymember);
^~~~~~
/tmp/31642023.c:33:22: error: incompatible integer to pointer conversion passing
'const char' to parameter of type 'char *' [-Werror,-Wint-conversion]
strcpy(texans, familymember);
^~~~~~
/tmp/31642023.c:33:22: error: incompatible integer to pointer conversion passing
'const char' to parameter of type 'char *' [-Werror,-Wint-conversion]
strcpy(texans, familymember);
^~~~~~
/tmp/31642023.c:36:27: error: result of comparison against a string literal is
unspecified (use strncmp instead) [-Werror,-Wstring-compare]
if (familymember == "end");
^ ~~~~~
/tmp/31642023.c:36:37: error: if statement has empty body [-Werror,-Wempty-body]
if (familymember == "end");
^
/tmp/31642023.c:36:37: note: put the semicolon on a separate line to silence
this warning
/tmp/31642023.c:40:144: error: format specifies type 'char *' but the argument
has type 'char' [-Werror,-Wformat]
...of family members currently residing in texas are %s\n", avg, texans);
~~ ^~~~~~
%c
/tmp/31642023.c:16:17: error: unused variable 'texas'
[-Werror,-Wunused-variable]
char state, texas;
^
/tmp/31642023.c:28:19: error: variable 'sum' is uninitialized when used here
[-Werror,-Wuninitialized]
sum = sum + age;
^~~
/tmp/31642023.c:17:19: note: initialize the variable 'sum' to silence this
warning
float avg, sum;
^
= 0.0
/tmp/31642023.c:25:23: error: variable 'members' is uninitialized when used here
[-Werror,-Wuninitialized]
members = members + 1;
^~~~~~~
/tmp/31642023.c:18:21: note: initialize the variable 'members' to silence this
warning
int age, members;
^
= 0
/tmp/31642023.c:40:144: error: variable 'texans' is uninitialized when used here
[-Werror,-Wuninitialized]
...of family members currently residing in texas are %s\n", avg, texans);
^~~~~~
/tmp/31642023.c:14:22: note: initialize the variable 'texans' to silence this
warning
const char texans;
^
= '\0'
15 errors generated.
至少,修复其中的每一个。
答案 1 :(得分:2)
int age, members;
{
printf("Enter family member or type end to output data when finished. \n");
{
你不需要那些内部块。您可以简单地删除这两个大括号({
)。或者你忘记在这里写一个循环?它看起来好像你希望内部代码多次运行。
if (familymember != "end")
您无法在C中将字符串与!=
进行比较。此行将比较内存地址,这不是您想要的。请改用strcmp(familymember, "end") != 0
。
members = members + 1;
此时 members
未初始化。您应该将其定义更改为int members = 0
。
scanf("%f", &age);
age
是int
。 scanf
%f
需要float
。您可能需要scanf("%d", &age)
。
sum = sum + age;
您尚未初始化sum
。您应该将其定义更改为float sum = 0.0
。
scanf("%s", &state);
scanf
%s
将字符串读入char
个数组。在这里,您可以指向单个char
。这会破坏随机存储器。您应该将state
数组设为familymember
(然后删除&
)。
if (state == "Texas")
你的编译器应该抱怨这个。您正在尝试将state
(这是一个整数)与"Texas"
(评估为指针)进行比较。将state
更改为数组后,您应该再次使用strcmp
。
strcpy(texans, familymember);
与上述相同的问题:您将texans
(整数)视为指针。看起来您打算将texans
作为一个计数,在这种情况下,它应该是int
(绝对不是const
)。
if (familymember == "end");
与上述问题相同:使用strcmp
比较字符串。此外,尾随;
是错误的,应该删除。有了它,您可以有效地创建一个空体的if
语句:
if (familymember == "end")
;
...
此外,这个条件可以简单地用else
替换。
printf("The average age of all family member's is %f and the number of family members currently residing in texas are %s\n", avg, texans);
将texans
更改为int
后,%s
应变为%d
。此外,member's
错误,应为members
。
如果这应该是一个循环,你应该在此时停止它(如"end"
暗示的那样)。你可能想要break;
。