已有 N 名學生的學號、成績存於結構體數組 s 中,需編寫函數 fun:
nNum 和成績 nScore。qsort 進行高效排序,需編寫比較函數 cmp 實現降序。 d:\\myfile.txt),遍歷排序後數組,格式化寫入。#include <stdio.h>
#include <stdlib.h>
#include <string.h>
typedef struct stu {
int nNum; // 學號
int nScore; // 成績
} STU;
// qsort 比較函數:按成績降序
int cmp(const void *a, const void *b) {
return (*(STU*)b).nScore - (*(STU*)a).nScore;
}
// 核心功能函數
void fun(STU *s, int n) {
// 1. 排序
qsort(s, n, sizeof(STU), cmp);
// 2. 寫入文件
FILE *fp = fopen("d:\\myfile.txt", "w");
if (fp == NULL) {
perror("文件打開失敗");
return;
}
for (int i = 0; i < n; i++) {
fprintf(fp, "%d %d\n", s[i].nNum, s[i].nScore);
}
fclose(fp);
printf("數據已成功寫入文件。\n");
}
// 主函數測試
int main() {
int n;
printf("請輸入學生人數: ");
scanf("%d", &n);
STU *s = (STU*)malloc(n * sizeof(STU));
if (s == NULL) {
printf("內存分配失敗\n");
return 1;
}
printf("請輸入 %d 名學生的學號和成績 (格式: 學號 成績):\n", n);
for (int i = 0; i < n; i++) {
scanf("%d %d", &s[i].nNum, &s[i].nScore);
}
fun(s, n);
// 驗證輸出
printf("\n排序後結果:\n學號 成績\n");
for (int i = 0; i < n; i++) {
printf("%d %d\n", s[i].nNum, s[i].nScore);
}
free(s);
return 0;
}
cmpconst void*,需強轉為 STU* 訪問成員。b - a 實現降序(大分在前),升序則為 a - b。(b>a)-(b<a) 代替減法。"w" 模式覆蓋寫入,確保文件內容即為最新排序結果。fprintf 格式化輸出,每行一條記錄,便於後續讀取解析。fopen 返回值,失敗時釋放資源並報錯。malloc 動態分配結構體數組,靈活適應任意 N。free(s) 釋放堆內存,防止洩漏。| 錯誤現象 | 原因 | 修正 |
|---|---|---|
| 排序結果錯誤 | 比較函數邏輯反、強轉類型錯誤 | 仔細核對 cmp 返回值邏輯與強轉語法 |
| 文件為空/亂碼 | 文件路徑轉義錯誤(雙反斜杠)、fprintf 格式串不匹配 | Windows路徑用 \\ 或正斜杠 /;檢查格式串 |
| 程序崩潰 | 未檢查 malloc/fopen 返回值、數組越界 | 添加錯誤判斷,邊界檢查 |
cmp 或增加參數)。qsort,理解算法內部機制。本題考察結構體數組操作、標準庫排序、文件讀寫、動態內存綜合應用。掌握 qsort + 比較函數模式是C語言排序的標準做法;文件操作要養成「檢查指針、格式化輸出、及時關閉」的好習慣。代碼結構清晰、錯誤處理完善,即為優秀解答。