|
|
|
|
@ -0,0 +1,119 @@
|
|
|
|
|
#include "student.h"
|
|
|
|
|
#include <stdio.h>
|
|
|
|
|
#include <string.h>
|
|
|
|
|
// 输入学生信息
|
|
|
|
|
void InputStudents(SqList *L, int n) {
|
|
|
|
|
if (L->length + n > 100) {
|
|
|
|
|
printf("警告:学生人数超过上限!\n");
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
for (int i = 0; i < n; i++) {
|
|
|
|
|
printf("输入第%d个学生信息(学号 姓名 成绩):", i+1);
|
|
|
|
|
Student s;
|
|
|
|
|
if (scanf("%d %s %f", &s.sid, s.name, &s.score) != 3) {
|
|
|
|
|
printf("输入格式错误!\n");
|
|
|
|
|
return; // 非法输入直接退出
|
|
|
|
|
}
|
|
|
|
|
L->data[L->length++] = s;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
// 显示学生信息
|
|
|
|
|
void PrintStudents(SqList L) {
|
|
|
|
|
printf("学号\t姓名\t成绩\n");
|
|
|
|
|
for (int i = 0; i < L.length; i++) {
|
|
|
|
|
printf("%d\t%s\t%.1f\n", L.data[i].sid, L.data[i].name, L.data[i].score);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
// 插入学生信息
|
|
|
|
|
int InsertStudent(SqList *L, int pos, Student s) {
|
|
|
|
|
if (pos < 1 || pos > L->length + 1 || L->length >= 100) {
|
|
|
|
|
return 0;
|
|
|
|
|
}
|
|
|
|
|
for (int i = L->length; i >= pos; i--) {
|
|
|
|
|
L->data[i] = L->data[i-1];
|
|
|
|
|
}
|
|
|
|
|
L->data[pos-1] = s;
|
|
|
|
|
L->length++;
|
|
|
|
|
return 1;
|
|
|
|
|
}
|
|
|
|
|
// 删除学生信息
|
|
|
|
|
int DeleteStudent(SqList *L, int pos) {
|
|
|
|
|
if (pos < 1 || pos > L->length) {
|
|
|
|
|
return 0;
|
|
|
|
|
}
|
|
|
|
|
for (int i = pos-1; i < L->length-1; i++) {
|
|
|
|
|
L->data[i] = L->data[i+1];
|
|
|
|
|
}
|
|
|
|
|
L->length--;
|
|
|
|
|
return 1;
|
|
|
|
|
}
|
|
|
|
|
// 统计学生个数
|
|
|
|
|
int GetStudentCount(SqList L) {
|
|
|
|
|
return L.length;
|
|
|
|
|
}
|
|
|
|
|
// 姓名排序(直接插入排序,稳定)
|
|
|
|
|
void InsertSortByName(SqList *L) {
|
|
|
|
|
for (int i = 1; i < L->length; i++) {
|
|
|
|
|
Student temp = L->data[i];
|
|
|
|
|
int j = i - 1;
|
|
|
|
|
while (j >= 0 && strcmp(temp.name, L->data[j].name) < 0) {
|
|
|
|
|
L->data[j+1] = L->data[j];
|
|
|
|
|
j--;
|
|
|
|
|
}
|
|
|
|
|
L->data[j+1] = temp;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
// 学号排序(快速排序,不稳定)
|
|
|
|
|
void QuickSortBySid(SqList *L) {
|
|
|
|
|
if (L->length <= 1) return;
|
|
|
|
|
quick_sort(L->data, 0, L->length - 1);
|
|
|
|
|
}
|
|
|
|
|
// 递归快速排序函数(处理Student数组)
|
|
|
|
|
void quick_sort(Student data[], int low, int high) {
|
|
|
|
|
if (low < high) {
|
|
|
|
|
// 分区操作,返回枢轴位置
|
|
|
|
|
int pivot_pos = partition(data, low, high);
|
|
|
|
|
// 递归排序左子数组
|
|
|
|
|
quick_sort(data, low, pivot_pos - 1);
|
|
|
|
|
// 递归排序右子数组
|
|
|
|
|
quick_sort(data, pivot_pos + 1, high);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
// 分区函数(单路快排,选择第一个元素作为枢轴)
|
|
|
|
|
int partition(Student data[], int low, int high) {
|
|
|
|
|
Student pivot = data[low]; // 保存枢轴元素(整个Student结构体)
|
|
|
|
|
int i = low; // 慢指针,指向当前处理位置
|
|
|
|
|
for (int j = low + 1; j <= high; j++) { // 快指针遍历数组
|
|
|
|
|
// 如果当前元素学号小于枢轴学号
|
|
|
|
|
if (data[j].sid < pivot.sid) {
|
|
|
|
|
i++; // 慢指针右移
|
|
|
|
|
// 交换data[i]和data[j]
|
|
|
|
|
Student temp = data[i];
|
|
|
|
|
data[i] = data[j];
|
|
|
|
|
data[j] = temp;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
// 将枢轴放到正确位置(i=low时无需交换)
|
|
|
|
|
if (i != low) {
|
|
|
|
|
Student temp = data[i];
|
|
|
|
|
data[i] = data[low];
|
|
|
|
|
data[low] = temp;
|
|
|
|
|
}
|
|
|
|
|
return i; // 返回枢轴位置
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//折半查找
|
|
|
|
|
Student* BinarySearch(SqList L, int sid) {
|
|
|
|
|
int low = 0, high = L.length - 1;
|
|
|
|
|
while (low <= high) {
|
|
|
|
|
int mid = (low + high) / 2;
|
|
|
|
|
if (L.data[mid].sid == sid) {
|
|
|
|
|
return &L.data[mid]; // 找到返回指针
|
|
|
|
|
} else if (L.data[mid].sid < sid) {
|
|
|
|
|
low = mid + 1;
|
|
|
|
|
} else {
|
|
|
|
|
high = mid - 1;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
return NULL;
|
|
|
|
|
}
|