Triplet(三元組)是線性表的一種特例,固定包含三個元素。本文展示一個符合 ADT 規範的完整 C 實現,涵蓋初始化、銷毀、存取、遍歷、排序判斷、最大/最小值查找等核心操作。
#define ERROR 0 #define OK 1 typedef int Status; typedef int ElemType; typedef ElemType *Triplet; // 三元組本質是指向動態數組的指針
Status InitTriplet(Triplet *T, ElemType v0, ElemType v1, ElemType v2) {
*T = (ElemType *)malloc(3 * sizeof(ElemType));
if (!*T) exit(-1); // 內存分配失敗終止程序
(*T)[0] = v0; (*T)[1] = v1; (*T)[2] = v2;
return OK;
}
Status DestroyTriplet(Triplet *T) {
free(*T);
*T = NULL; // 防止野指針
return OK;
}
注意:傳遞 Triplet *T(二級指針)以便在函數內修改主調函數中的指針值。
Status Get(Triplet T, int i, ElemType *e) { // 讀取第 i 個元素 (1~3)
if (i < 1 || i > 3 || T == NULL) return ERROR;
*e = T[i - 1]; // 內部 0-based 索引
return OK;
}
Status Put(Triplet T, int i, ElemType e) { // 修改第 i 個元素
if (T == NULL || i < 1 || i > 3) return ERROR;
T[i - 1] = e; // 同樣需轉換索引
return OK;
}
原代碼中 Put 存在 T[i] = e 的越界錯誤,此處已修正。
Status IsAscending(Triplet T) { // 非遞減
return (T[0] <= T[1] && T[1] <= T[2]);
}
Status IsDescending(Triplet T) { // 非遞增
return (T[0] >= T[1] && T[1] >= T[2]);
}
Status Max(Triplet T, ElemType *e) {
*e = (T[0] > T[1] ? T[0] : T[1]);
*e = (*e > T[2]) ? *e : T[2];
return OK;
}
// Min 邏輯對稱
void main() {
Triplet T;
ElemType val, maxVal, minVal;
Status stat;
stat = InitTriplet(&T, 0, 1, 2); // 初始化 0,1,2
Get(T, 1, &val); // 讀取首元素 → 0
Put(T, 1, 5); // 修改首元素為 5 → 三元組變 5,1,2
Show(T); // 遍歷輸出
// 判斷有序性
printf(IsAscending(T) ? "升序\n" : "非升序\n"); // 非升序
printf(IsDescending(T) ? "降序\n" : "非降序\n"); // 非降序
Max(T, &maxVal); // 最大值 5
DestroyTriplet(&T); // 釋放內存
// 錯誤演示:Min(T, &minVal) 在 Destroy 後調用 → 訪問已釋放內存,行為未定義
}
DestroyTriplet 後不可再訪問該 Triplet,否則產生未定義行為(UAF)。T == NULL 與下標合法性。Status 返回碼 + 輸出參數模式,而非異常拋出。此實現展示了 C 語言構建 ADT 的經典模式:不透明指針 + 動態分配 + 狀態碼返回,為大型系統模塊化奠定基礎。