简体   繁体   English

为什么我在 C 中得到错误的平均值?

[英]Why am I getting the wrong average in C?

I'm new at this and having some trouble.我是新手,遇到了一些麻烦。 I'm trying to find the average of the grades that are inputed by the user but I realized that if you use a decimal in any of the grades, it's just being calculated as if they are whole numbers.我试图找到用户输入的成绩的平均值,但我意识到如果你在任何成绩中使用小数,它只是被计算为好像它们是整数。

#include <stdio.h>

int main(void)
{
    unsigned int counter;
    float grade;
    int total;
    float average;
    int number;
    
    total = 0;
    counter = 1;
    
    printf("Number of scores to enter:\t");
    scanf("%d", &number);

    printf("\n");
    
    while (counter <= number) {
        printf("%s%d%s", "Enter the score for Lab ", counter, ":\t");
        scanf("%f", &grade);
        total = total + grade;
        counter = counter + 1;
    }
    
    printf("\n");
    
    average = (float) total / number;
    
    printf("Average lab score: %.1f\n", average);
    
    if (grade>=90) {
        puts("Letter grade: A");
    }
    else if (grade>=80) {
        puts("Letter grade: B");
    }
    else if (grade>=70) {
        puts("Letter grade: C");
    }
    else if (grade>=60) {
        puts("Letter grade: D");
    }
    else {
        puts("Letter grade: F");
    }

    return 0;
}

You are capturing scanf("%f", &grade);您正在捕获scanf("%f", &grade); as a float and then calculating total = total + grade;作为浮点数,然后计算total = total + grade; . .

You have defined int total;你已经定义了int total; . . You would need to define it as float total;您需要将其定义为float total; . .

You are moving a float variable into an integer which is truncating the decimals you had previously entered.您正在将一个浮点变量移动到一个整数中,该整数会截断您之前输入的小数。

There's no need to ask up front how many data points will be entered.无需预先询问将输入多少数据点。 Indeed, that is an anti-pattern.确实,这是一种反模式。 Just do something like:只需执行以下操作:

#include <stdio.h>

int
main(void)
{
        unsigned int count = 0;
        float grade;
        float total = 0.0;
        float average;

        while( scanf("%f", &grade) == 1 ) {
                total += grade;
                count += 1;
        }
        average = total / (float) count;
        printf("Average lab score: %.1f\n", average);
        fputs("Letter grade: ", stdout);
        putchar( average >= 90.0 ? 'A' : average >= 80.0 ? 'B' :
                average >= 70.0 ? 'C' : average >= 60.0 ? 'D' : 'F');
        putchar('\n');

        return average >= 60.0;
}

$ echo 78.2 96.5 80 | ./a.out
Average lab score: 84.9
Letter grade: B

Key points: total needs to be a float type.要点: total需要是浮点型。 You must check the value returned by scanf .必须检查scanf返回的值。 Always.总是。 Probably you want to handle bad input more cleanly that this does.可能你想比这更干净地处理错误的输入。 This just throws away all data after an error and computes the average based on whatever data was entered prior to the error.这只是在出错后丢弃所有数据,并根据出错前输入的任何数据计算平均值。 A cleaner solution would abort with an error message.更干净的解决方案将中止并显示错误消息。 Exercise left for the reader.练习留给读者。

A reasonable argument can be made that this is an abuse of the ternary operator;可以合理地认为这是对三元运算符的滥用; however you want to refactor it, don't repeat yourself by hardcoding the string "Letter grade: " multiple times.但是你想重构它,不要通过多次硬编码字符串“Letter Grade:”来重复自己。

Rather than abusing the ternary operator as above, you may prefer something like:与其像上面那样滥用三元运算符,您可能更喜欢这样的操作:

#include <stdio.h>

int
main(void)
{
        unsigned int count = 0;
        float grade;
        float total = 0.0;
        float average;

        while( scanf("%f", &grade) == 1 ) {
                total += grade;
                count += 1;
        }
        average = total / (float) count;
        int s = 'A' + (99 - (int)average) / 10;
        printf("Average lab score: %.1f\n", average);
        printf("Letter grade: %c\n", s > 'D' ? 'F' : s);

        return average >= 60.0;
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM