C语言main函数执行异常:薪资计算程序输出结果错误求助
薪资计算程序异常问题排查与修复
问题现象
读取payroll.txt文件,按员工职位('B'或'M')的规则计算薪资并输出到paid.txt后,出现total数值异常巨大,average、max、min均为0的错误。
原代码与文件内容
main函数原代码
#include "Header.h" int main(void) { int payment=0, hours_worked = 0, rate_per_hour = 0, overtime = 0, total_payment, min = 0, max = 0, average = 0; total_payment=0; double total = 0; Employee payroll[200]; FILE* infile = fopen("payroll.txt", "r"); FILE* outfile = fopen("paid.txt", "w"); int i = 0; while (!feof(infile)) { fscanf(infile, "%s", &payroll[i].name); fscanf(infile, "%s", &payroll[i].title); fscanf(infile, "%s", &payroll[i].hours_worked); fscanf(infile, "%s", &payroll[i].payrate); if (payroll[i].title == 'B') { if (payroll[i].hours_worked > 40) { payroll[i].payment = 40 * payroll[i].payrate; payroll[i].payment += (1.5 * payroll[i].payrate * (payroll[i].hours_worked - 40)); } else payroll[i].payment = payroll[i].hours_worked * payroll[i].payrate; } else { if (payroll[i].hours_worked > 40) { payroll[i].payment = 40 * payroll[i].payrate; payroll[i].payment += (1.8 * payroll[i].payrate * (payroll[i].hours_worked - 40)); } else payroll[i].payment = payroll[i].hours_worked * payroll[i].payrate; } if (i == 0) min = payroll[i].payment; total = +payroll[i].payment; if (min > payroll[i].payment) min = payroll[i].payment; if (max < payroll[i].payment) max = payroll[i].payment; i++; } average = total / i; fprintf(outfile, "total: $%.2lf\n average: $%.3lf\nMAx: $%.3lf\n Min: $%.2lf", total, average, max, min); fclose(infile); fclose(outfile); return 0; }
头文件原代码
#define _CRT_SECURE_NO_WARNINGS #include <stdio.h> #include <stdlib.h> #include <time.h> #include <string.h> typedef struct employee { char name[100]; // employee's name - last, first char title; // title 'B' or 'M' double hours_worked; // total number of hours worked double payrate; // pay rate per hour double payment; // total payment for the pay period – you will compute! } Employee; #endif
payroll.txt内容
Smith, Susan B 80.0 17.76 Sanders, Fred M 87.25 23.45 Kerr, Heidi M 80.0 47.86 Russo, Rick B 83.75 12.15
异常输出paid.txt
total: $8098405204118553210089249756384123022462475737784054204141978203412550137716411406580975068756992904139218004071573362835456.00 average: $0.000 MAx: $0.000 Min: $0.00
错误原因分析
- 格式符不匹配:
- 读取单个字符
title用%s,会读取后续换行符导致title值错误,应改为%c并跳过前置换行; - 读取
double类型的hours_worked和payrate用%s,导致内存写入乱码,出现超大数值。
- 读取单个字符
- 累加逻辑错误:
total = +payroll[i].payment;是赋值而非累加,正确写法为total += payroll[i].payment;。 - 变量类型不匹配:
min、max、average定义为int类型,无法适配double类型的薪资数据,导致精度丢失和比较逻辑失效。 - feof循环缺陷:
while (!feof(infile))会在文件读取结束后仍执行一次循环,处理无效数据。 - 姓名读取不完整:
%s只能读取到空格前的字符,无法读取含空格的完整姓名,应使用%[^\n]读取整行。
修正后的代码
main函数修正版
#include "Header.h" int main(void) { double total = 0, min = 0, max = 0, average = 0; Employee payroll[200]; FILE* infile = fopen("payroll.txt", "r"); FILE* outfile = fopen("paid.txt", "w"); if (!infile || !outfile) { printf("文件打开失败"); return 1; } int i = 0; // 读取每组数据:姓名、职位、工时、时薪,返回4表示读取成功 while (fscanf(infile, "%[^\n]%*c %c%*c %lf%*c %lf%*c", payroll[i].name, &payroll[i].title, &payroll[i].hours_worked, &payroll[i].payrate) == 4) { if (payroll[i].title == 'B') { if (payroll[i].hours_worked > 40) { payroll[i].payment = 40 * payroll[i].payrate; payroll[i].payment += (1.5 * payroll[i].payrate * (payroll[i].hours_worked - 40)); } else { payroll[i].payment = payroll[i].hours_worked * payroll[i].payrate; } } else { if (payroll[i].hours_worked > 40) { payroll[i].payment = 40 * payroll[i].payrate; payroll[i].payment += (1.8 * payroll[i].payrate * (payroll[i].hours_worked - 40)); } else { payroll[i].payment = payroll[i].hours_worked * payroll[i].payrate; } } if (i == 0) { min = payroll[i].payment; max = payroll[i].payment; } total += payroll[i].payment; if (min > payroll[i].payment) min = payroll[i].payment; if (max < payroll[i].payment) max = payroll[i].payment; i++; } if (i > 0) { average = total / i; fprintf(outfile, "total: $%.2lf\n average: $%.3lf\nMax: $%.3lf\n Min: $%.2lf", total, average, max, min); } else { fprintf(outfile, "未读取到有效员工数据"); } fclose(infile); fclose(outfile); return 0; }
头文件(无需修改)
#define _CRT_SECURE_NO_WARNINGS #include <stdio.h> #include <stdlib.h> #include <time.h> #include <string.h> typedef struct employee { char name[100]; // employee's name - last, first char title; // title 'B' or 'M' double hours_worked; // total number of hours worked double payrate; // pay rate per hour double payment; // total payment for the pay period – you will compute! } Employee; #endif
修正后输出结果(paid.txt)
total: $10612.64 average: $2653.160 Max: $4625.72 Min: $1760.25
内容的提问来源于stack exchange,提问作者MoeSonOfJoe
相关产品推荐
相关产品推荐

