1. 程式人生 > >C/C++動態自定義結構體陣列例項鍛鍊-學生成績排序

C/C++動態自定義結構體陣列例項鍛鍊-學生成績排序

/************************************************************************/
/* 本程式是對動態記憶體、動態陣列、結構體、函式的綜合應用。    */
/************************************************************************/

#include <STDIO.H>
#include <MALLOC.H>


int input(int *,struct Student *);
int line(int, struct Student *);
int output(int, struct Student *);

struct Student  
{
	int age;
	char name[15];
	float score;
};

int main(void)
{
	int num;
	float f;
	printf("請輸入學生的個數:\n");
	printf("N = ");
	scanf("%d", &num); 
	struct Student * q = (struct Student *)malloc(num * sizeof(struct Student));//定義結構體指標變數,同時利用動態記憶體分配技術為 q 申請動態記憶體空間,最終算是定義了一個動態陣列,指標變數 q 指向了此空間的首地址.此陣列的資料型別是自定義資料型別 struct Student.
	
	input(&num, q);//對一個數組的操作至少需要兩個引數:陣列首地址,陣列長度。下同
	line(num, q);
	output(num, q);
	f = q[0].score - q[num-1].score;//結構體的分量是可以進行相關運算的
	printf("第一名 %s 和最後一名 %s 分數相差:%f\n", q[0].name, q[num-1].name, f);
	
	free(q);//將變數釋放掉就是釋放了其空間,因為變數不存在了,其原來所佔的空間成為了“無主”空間,即達到了釋放動態記憶體的目的。	
	return 0;
}

//input實現對學生資訊的輸入。
int input(int * p, struct Student * q)
{	
	for (int i=0; i<(*p); ++i)//p存放的是變數的地址,* p 則是對取地址的逆運算,即是此地址處變數的值
	{
		printf("請輸入第%d個學生的資訊(依次是年齡、姓名、分數,用空格隔開):\n", i+1);
		scanf("%d %s %f", &q[i].age, q[i].name, &q[i].score);//q雖然是值傳遞,但這值本身是個地址,所以實際其實地址傳遞。地址傳遞的操作才可以對原資料進行修改。q是動態陣列的首地址,當然可以同普通陣列一樣對某個元素進行操作,只是此陣列的元素的資料型別是個自定義的資料型別-結構體,所以要根據結構體中的每個成員具體資料型別的來處理,比如此處的q[i].name是字串型別變數,那麼對它的輸入就要同普通字串的輸入格式一樣,寫字串名(即是字串的首地址)即可,再如q[i].age是整型變數,那麼對其進行輸入時就要加上取地址符 & .
	}
	
	return 0;
}

//line實現將輸入的學生資訊按分數從高到低排序。
int line(int j, struct Student * k)
{
	struct Student st;
	for (int t=0; t<j; ++t)//氣泡排序經典演算法,此處按降序排序
	{
		for (int i=0; i<(j-t-1); ++i)
		{
			if(k[i].score<k[i+1].score)//當分數比後邊的小時就交換彼此的資料。
			{
				st = k[i];//結構體變數不允許相互加減乘除(實際上也是沒有意義的,但結構體的分量卻是可以進行相應的運算的),但可以相互賦值,當整體相互賦值時,其各自對應的成員會自動交換資料。
				k[i] = k[i+1];
				k[i+1] = st;
			}
		}
	}
	
	return 0;
}

//output實現按照學生分數從高到低輸出學生姓名。
int output(int k, struct Student * p)
{
	printf("按照學生成績從高到低排序為:\n");
	for (int i=0; i<k; ++i)
	{
		printf("%s  ", p[i].name);
	}
	printf("\n");

	return 0;
}
/************************************************************************/
/* 該程式在VC++6.0中執行結果如下:
請輸入學生的個數:
N = 5
請輸入第1個學生的資訊(依次是年齡、姓名、分數,用空格隔開):
20 劉漢陽 69.8
請輸入第2個學生的資訊(依次是年齡、姓名、分數,用空格隔開):
24 樸玫麗 90.5
請輸入第3個學生的資訊(依次是年齡、姓名、分數,用空格隔開):
21 努爾哈赤 96
請輸入第4個學生的資訊(依次是年齡、姓名、分數,用空格隔開):
22 一婷 98.6
請輸入第5個學生的資訊(依次是年齡、姓名、分數,用空格隔開):
21 笑邦 68.6
按照學生成績從高到低排序為:
一婷  努爾哈赤  樸玫麗  劉漢陽  笑邦
第一名 一婷 和最後一名 笑邦 分數相差:30.000000
Press any key to continue                       */
/************************************************************************/