C语言学生随机抽号演讲计分系统

项目描述

设计一款用于课程任务检查或比赛计分的软件,基本功能:
(1)设置本课程的学生总数
(2)根据本次参与的学生总数,随机抽取一个还未汇报演讲的学生的学号。
(3)每个学生汇报演讲完毕,输入该学生的得分(假设有5个评委,则需输入5个成绩)。
(4)计算该选手的得分:去掉最高分和最低分,其余的分数求平均,并显示选手序号、姓名、得分。
(5)输出参加比赛过的所有学生的成绩及当前排名。
(6)对演讲过的学生作上标记,下次程序运行时不再抽取该学号。
(7)每次退出程序时(不一定一次能进行完所有的学生的汇报,可以分多次进行),将学生的序号、姓名、成绩写入文件。
(8)结束对学生成绩进行排序,显示,并按照一等奖10%、二等奖20%、三等奖30%的比例确定选手的获奖名次,并将结果写入文件保存。
拓展功能:赛前事先输入评委人数,设置选手姓名、序号,选手上场顺序由程序随机抽取,已经抽取过的选手信息在文件中做出标记,下次不再抽取。其他更多方便用户使用的功能。

实现代码

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <string.h>

#define MAX_STUDENTS 100 // 最大学生数
#define MAX_NAME_LEN 20 // 最大姓名长度
#define MAX_SCORES 5 // 每个学生的成绩数
#define FILE_NAME "scores.txt" // 存储成绩的文件名

// 学生结构体
struct student {
    char name[MAX_NAME_LEN];
    float scores[MAX_SCORES];
    int reported; // 是否已汇报演讲
};

// 抽取未汇报演讲的学生的序号
int draw_student(struct student students[], int total_students) {
    int i, index;
    do {
        index = rand() % total_students;
    } while (students[index].reported);
    return index;
}

// 输入一个学生的成绩
void input_scores(struct student *s) {
    int i;
    printf("请输入 %s 的成绩:\n", s->name);
    for (i = 0; i < MAX_SCORES; i++) {
        scanf("%f", &s->scores[i]);
    }
}

// 计算一个学生的得分
float calculate_score(struct student *s) {
    int i;
    float sum = 0, max = 0, min = 100;
    for (i = 0; i < MAX_SCORES; i++) {
        if (s->scores[i] > max) { max = s->scores[i]; }
        if (s->scores[i] < min) { min = s->scores[i]; }
        sum += s->scores[i];
    }
    return (sum - max - min) / (MAX_SCORES - 2);
}

// 输出参加比赛的所有学生的成绩及当前排名
void output_scores(struct student students[], int total_students) {
    int i, j;
    float scores[MAX_STUDENTS];
    char names[MAX_STUDENTS][MAX_NAME_LEN];
    for (i = 0; i < total_students; i++) {
        scores[i] = calculate_score(&students[i]);
        strcpy(names[i], students[i].name);
    }
    // 冒泡排序
    for (i = 0; i < total_students - 1; i++) {
        for (j = 0; j < total_students - 1 - i; j++) {
            if (scores[j] < scores[j+1]) {
                float temp_score = scores[j];
                scores[j] = scores[j+1];
                scores[j+1] = temp_score;
                char temp_name[MAX_NAME_LEN];
                strcpy(temp_name, names[j]);
                strcpy(names[j], names[j+1]);
                strcpy(names[j+1], temp_name);
            }
        }
    }
    printf("成绩单:\n");
    for (i = 0; i < total_students; i++) {
        printf("%d. %s:%.2f\n", i+1, names[i], scores[i]);
    }
}

// 写入成绩文件
void write_scores(struct student students[], int total_students) {
    int i;
    FILE *fp = fopen(FILE_NAME, "w");
    if (!fp) {
        printf("无法打开文件 %s\n", FILE_NAME);
        return;
    }
    for (i = 0; i < total_students; i++) {
        fprintf(fp, "%s ", students[i].name);
        int j;
        for (j = 0; j < MAX_SCORES; j++) {
            fprintf(fp, "%.2f ", students[i].scores[j]);
        }
        fprintf(fp, "\n");
    }
    fclose(fp);
}

// 读取成绩文件
void read_scores(struct student students[], int total_students) {
    int i;
    FILE *fp = fopen(FILE_NAME, "r");
    if (!fp) { return; }
    while (!feof(fp)) {
        char name[MAX_NAME_LEN];
        fscanf(fp, "%s", name);
        for (i = 0; i < total_students; i++) {
            if (strcmp(students[i].name, name) == 0) {
                int j;
                for (j = 0; j < MAX_SCORES; j++) {
                    fscanf(fp, "%f", &students[i].scores[j]);
                }
                students[i].reported = 1;
                break;
            }
        }
    }
    fclose(fp);
}

int main() {
    srand(time(NULL)); // 设置随机种子
    struct student students[MAX_STUDENTS];
    int total_students, i;
    printf("请输入学生总数:");
    scanf("%d", &total_students);
    if (total_students > MAX_STUDENTS) {
        printf("学生总数不能超过 %d\n", MAX_STUDENTS);
        return 0;
    }
    for (i = 0; i < total_students; i++) {
        printf("请输入第 %d 个学生的姓名:", i+1);
        scanf("%s", students[i].name);
        students[i].reported = 0;
    }
    read_scores(students, total_students);
    while (1) {
        int index = draw_student(students, total_students);
        printf("下一个汇报演讲的学生是:%s\n", students[index].name);
        input_scores(&students[index]);
        float score = calculate_score(&students[index]);
        printf("%s 的得分是:%.2f\n", students[index].name, score);
        write_scores(students, total_students);
        output_scores(students, total_students);
        students[index].reported = 1;
        int finished = 1;
        for (i = 0; i < total_students; i++) {
            if (!students[i].reported) { finished = 0; }
        }
        if (finished) { break; }
    }
    output_scores(students, total_students);
    return 0;
}

此代码实现了基本功能,包括随机抽号、输入成绩、计算得分、输出排名等功能,并支持将成绩写入文件和从文件中读取成绩。对于拓展功能,可以根据需要进行修改和扩展。

效果截图

图片[1]-C语言学生随机抽号演讲计分系统-QQ沐编程

© 版权声明
THE END
喜欢就支持一下吧
点赞5赞赏 分享