資料結構:使用C++模板設計順序棧和佇列的抽象資料型別(ADT),結構體型,型別,鏈棧和鏈佇列的實現
阿新 • • 發佈:2022-04-12
模板設計順序棧和佇列的抽象資料型別(ADT),結構體型,型別,鏈棧和鏈佇列的實現
一、棧
1、Struct:
1 /***順序棧的實現***/ 2 3 //順序棧定義 4 #define OK 1 5 #define ERROR 0 6 #define OVERFLOW -2 7 #define MAXSIZE 100//順序棧儲存空間的初始分配量 8 typedef int Status; 9 typedef int SElemType; 10 11 typedef struct { 12 SElemType *base;//棧底指標 13 SElemType *top;//Stack struct code棧頂指標 14 int stacksize;//棧可用的最大容量 15 } SqStack; 16 17 //演算法3.1 順序棧的初始化 18 Status InitStack(SqStack &S) { 19 //構造一個空棧S 20 S.base = new SElemType[MAXSIZE];//為順序棧動態分配一個最大容量為MAXSIZE的陣列空間 21 if (!S.base) 22 return OVERFLOW; //儲存分配失敗 23 S.top = S.base; //top初始為base,空棧 24 S.stacksize = MAXSIZE; //stacksize置為棧的最大容量MAXSIZE 25 return OK; 26 } 27 //演算法3.2 順序棧的入棧 28 Status Push(SqStack &S, SElemType e) { 29 // 插入元素e為新的棧頂元素 30 if (S.top - S.base == S.stacksize) 31 return ERROR; //棧滿 32 *(S.top++) = e; //元素e壓入棧頂,棧頂指標加1 33 return OK; 34 } 35 //演算法3.3 順序棧的出棧 36 Status Pop(SqStack &S, SElemType &e) {37 //刪除S的棧頂元素,用e返回其值 38 if (S.base == S.top) 39 return ERROR;//棧空 40 e = *(--S.top); //棧頂指標減1,將棧頂元素賦給e 41 return OK; 42 } 43 //演算法3.4 取順序棧的棧頂元素 44 SElemType GetTop(SqStack S) {//返回S的棧頂元素,不修改棧頂指標 45 if (S.top != S.base) //棧非空 46 return *(S.top - 1); //返回棧頂元素的值,棧頂指標不變 47 } 48 bool StackEmpty( SqStack S ) 49 { 50 if(S.top == S.base) return true; 51 else return false; 52 } 53 int StackLength( SqStack S ) 54 { 55 return S.top - S.base; 56 } 57 Status ClearStack( SqStack S ) 58 { 59 if( S.base ) S.top = S.base; 60 return OK; 61 } 62 Status DestroyStack( SqStack &S ) 63 { 64 if( S.base ) 65 { 66 delete S.base ; 67 S.stacksize = 0; 68 S.base = S.top = NULL; 69 } 70 return OK; 71 }
2、Class
1 /***順序棧的實現***/ 2 #include<iostream> 3 using namespace std; 4 //順序棧定義 5 #define OK 1 6 #define ERROR 0 7 #define OVERFLOW -2 8 #define MAXSIZE 100//順序棧儲存空間的初始分配量 9 typedef int Status; 10 11 template<class SElemType> 12 class SqStack 13 { 14 private: 15 SElemType *base;//棧底指標 16 SElemType *top;//棧頂指標 17 int stacksize;//棧可用的最大容量 18 public: 19 SqStack(); 20 Status Push(SElemType e); 21 Status Pop(SElemType &e); 22 ~SqStack( ); 23 //過載函式:賦值 24 SqStack<SElemType> operator=(SqStack<SElemType> &s); 25 //拷貝建構函式 26 SqStack(const SqStack<SElemType> &s); 27 28 SElemType GetTop() //返回S的棧頂元素,不修改棧頂指標 29 { 30 if (top != base) //棧非空 31 return *(top - 1); //返回棧頂元素的值,棧頂指標不變 32 } 33 bool StackEmpty( ) 34 { 35 if(top == base) 36 return true; 37 else 38 return false; 39 } 40 int StackLength( ) 41 { 42 return top - base; 43 } 44 Status ClearStack( ) 45 { 46 if( base ) 47 top = base; 48 return OK; 49 } 50 } ; 51 52 template<class SElemType> 53 SqStack<SElemType>::SqStack() 54 { 55 //構造一個空棧S 56 base = new SElemType[MAXSIZE];//為順序棧動態分配一個最大容量為MAXSIZE的陣列空間 57 top = base; //top初始為base,空棧 58 stacksize = MAXSIZE; //stacksize置為棧的最大容量MAXSIZE 59 } 60 template<class SElemType> 61 Status SqStack<SElemType>::Push(SElemType e) 62 { 63 // 插入元素e為新的棧頂元素 64 if (top - base == stacksize) 65 return ERROR; //棧滿 66 *(top++) = e; //元素e壓入棧頂,棧頂指標加1 67 return OK; 68 } 69 template<class SElemType> 70 Status SqStack<SElemType>::Pop(SElemType &e) 71 { 72 //刪除S的棧頂元素,用e返回其值 73 if (base == top) 74 return ERROR;//棧空 75 e = *(--top); //棧頂指標減1,將棧頂元素賦給e 76 return OK; 77 } 78 79 template<class SElemType> 80 SqStack<SElemType>::~SqStack( ) 81 { 82 if( base ) 83 { 84 delete []base ; 85 } 86 } 87 //過載函式:賦值 88 template<class SElemType> 89 SqStack<SElemType> SqStack<SElemType>::operator=(SqStack<SElemType> &s) 90 { 91 base = new SElemType[MAXSIZE];//為順序棧動態分配一個最大容量為MAXSIZE的陣列空間 92 top = base+s.StackLength(); 93 for(int i=0; i<s.StackLength(); i++) 94 { 95 base[i]=s.base[i]; 96 } 97 stacksize = MAXSIZE; //stacksize置為棧的最大容量MAXSIZE 98 return *this; 99 } 100 //拷貝建構函式 101 template<class SElemType> 102 SqStack<SElemType>::SqStack(const SqStack<SElemType> &s) 103 { 104 base = new SElemType[MAXSIZE];//為順序棧動態分配一個最大容量為MAXSIZE的陣列空間 105 top = base+s.StackLength(); 106 for(int i=0; i<s.StackLength(); i++) 107 { 108 base[i]=s.base[i]; 109 } 110 stacksize = MAXSIZE; //stacksize置為棧的最大容量MAXSIZE 111 }Stack class code
3、Link
1 /***鏈棧的實現***/ 2 #include<iostream> 3 4 #define OK 1 5 #define ERROR 0 6 #define OVERFLOW -2 7 typedef int Status; 8 typedef char SElemType; 9 10 typedef struct StackNode { 11 SElemType data; 12 struct StackNode *next; 13 } StackNode, *LinkStack; 14 15 //演算法3.5 鏈棧的初始化 16 Status InitStack(LinkStack &S) { // 構造一個空棧 S,棧頂指標置空 17 S = NULL; 18 return OK; 19 } 20 21 //演算法3.6 鏈棧的入棧 22 Status Push(LinkStack &S, SElemType e) {//在棧頂插入元素e 23 LinkStack p; 24 p = new StackNode; //生成新結點 25 p->data = e; //將新結點資料域置為e 26 p->next = S; //將新結點插入棧頂 27 S = p; //修改棧頂指標為p 28 return OK; 29 } 30 31 //演算法3.7 鏈棧的出棧 32 Status Pop(LinkStack &S, SElemType &e) {//刪除S的棧頂元素,用e返回其值 33 LinkStack p; 34 if (S == NULL) 35 return ERROR; //棧空 36 e = S->data; //將棧頂元素賦給e 37 p = S; //用p臨時儲存棧頂元素空間,以備釋放 38 S = S->next; //修改棧頂指標 39 delete p; //釋放原棧頂元素的空間 40 return OK; 41 } 42 //演算法3.8 取鏈棧的棧頂元素 43 SElemType GetTop(LinkStack S) {//返回S的棧頂元素,不修改棧頂指標 44 if (S != NULL) //棧非空 45 return S->data; //返回棧頂元素的值,棧頂指標不變 46 } 47 bool StackEmpty(LinkStack S) { 48 if (!S) 49 return true; 50 return false; 51 }Stack link code
二、
1、Struct
1 /***迴圈佇列基本操作***/ 2 3 #define MAXQSIZE 100 4 #define OK 1 5 #define ERROR 0 6 #define OVERFLOW -2 7 typedef char QElemType; 8 typedef int Status; 9 10 typedef struct { 11 QElemType *base;//初始化時動態分配儲存空間 12 int front;//頭指標 13 int rear;//尾指標 14 } SqQueue; 15 16 //演算法3.11 迴圈佇列的初始化 17 Status InitQueue(SqQueue &Q) {//構造一個空佇列Q 18 Q.base = new QElemType[MAXQSIZE]; //為佇列分配一個最大容量為MAXSIZE的陣列空間 19 if (!Q.base) 20 return OVERFLOW; //儲存分配失敗 21 Q.front = Q.rear = 0; //頭指標和尾指標置為零,佇列為空 22 return OK; 23 } 24 25 //演算法3.12 求迴圈佇列的長度 26 int QueueLength(SqQueue Q) {//返回Q的元素個數,即佇列的長度 27 return (Q.rear - Q.front + MAXQSIZE) % MAXQSIZE; 28 } 29 30 //演算法3.13 迴圈佇列的入隊 31 Status EnQueue(SqQueue &Q, QElemType e) {//插入元素e為Q的新的隊尾元素 32 if ((Q.rear + 1) % MAXQSIZE == Q.front) //尾指標在迴圈意義上加1後等於頭指標,表明隊滿 33 return ERROR; 34 Q.base[Q.rear] = e; //新元素插入隊尾 35 Q.rear = (Q.rear + 1) % MAXQSIZE; //隊尾指標加1 36 return OK; 37 } 38 39 //演算法3.14 迴圈佇列的出隊 40 Status DeQueue(SqQueue &Q, QElemType &e) {//刪除Q的隊頭元素,用e返回其值 41 if (Q.front == Q.rear) 42 return ERROR; //隊空 43 e = Q.base[Q.front]; //儲存隊頭元素 44 Q.front = (Q.front + 1) % MAXQSIZE; //隊頭指標加1 45 return OK; 46 } 47 48 //演算法3.15 取迴圈佇列的隊頭元素 49 QElemType GetHead(SqQueue Q) {//返回Q的隊頭元素,不修改隊頭指標 50 if (Q.front != Q.rear) //佇列非空 51 return Q.base[Q.front]; //返回隊頭元素的值,隊頭指標不變 52 }Queue Struct node
2、Class
1 /***迴圈佇列基本操作***/ 2 #include<iostream> 3 using namespace std; 4 #define MAXQSIZE 100 5 #define OK 1 6 #define ERROR 0 7 #define OVERFLOW -2 8 9 typedef int Status; 10 template<class QElemType> 11 class SqQueue 12 { 13 private: 14 QElemType *base;//初始化時動態分配儲存空間 15 int front;//頭指標 16 int rear;//尾指標 17 public: 18 SqQueue(); 19 Status EnQueue(QElemType e); 20 Status DeQueue(QElemType &e); 21 QElemType GetHead(); 22 ~SqQueue( ); 23 //過載函式:賦值 24 SqQueue<QElemType> operator=(SqQueue<QElemType> &q); 25 //拷貝建構函式 26 SqQueue(const SqQueue<QElemType> &q); 27 int QueueLength() //返回Q的元素個數,即佇列的長度 28 { 29 return (rear - front + MAXQSIZE) % MAXQSIZE; 30 } 31 bool QueueEmpty() 32 { 33 if (front == rear) //隊空 34 return true; 35 else 36 return false; 37 } 38 } ; 39 template<class QElemType> 40 SqQueue<QElemType>::SqQueue() //構造一個空佇列Q 41 { 42 base = new QElemType[MAXQSIZE]; //為佇列分配一個最大容量為MAXSIZE的陣列空間 43 front = rear = 0; //頭指標和尾指標置為零,佇列為空 44 } 45 46 template<class QElemType> 47 Status SqQueue<QElemType>::EnQueue(QElemType e) //插入元素e為Q的新的隊尾元素 48 { 49 if ((rear + 1) % MAXQSIZE == front) //尾指標在迴圈意義上加1後等於頭指標,表明隊滿 50 return ERROR; 51 base[rear] = e; //新元素插入隊尾 52 rear = (rear + 1) % MAXQSIZE; //隊尾指標加1 53 return OK; 54 } 55 56 template<class QElemType> 57 Status SqQueue<QElemType>::DeQueue(QElemType &e) //刪除Q的隊頭元素,用e返回其值 58 { 59 if (front == rear) 60 return ERROR; //隊空 61 e = base[front]; //儲存隊頭元素 62 front = (front + 1) % MAXQSIZE; //隊頭指標加1 63 return OK; 64 } 65 66 template<class QElemType> 67 QElemType SqQueue<QElemType>::GetHead() //返回Q的隊頭元素,不修改隊頭指標 68 { 69 if (front != rear) //佇列非空 70 return base[front]; //返回隊頭元素的值,隊頭指標不變 71 } 72 template<class QElemType> 73 SqQueue<QElemType>::~SqQueue( ) 74 { 75 if( base ) 76 { 77 delete []base ; 78 } 79 } 80 //過載函式:賦值 81 template<class QElemType> 82 SqQueue<QElemType> SqQueue<QElemType>::operator=(SqQueue<QElemType> &q) 83 { 84 base = new QElemType[MAXQSIZE]; 85 front = q.front; 86 rear = q.rear; 87 88 for(int i=0; i<MAXQSIZE; i++)//複製整個陣列 89 { 90 base[i]=q.base[i]; 91 } 92 return *this; 93 } 94 //拷貝建構函式 95 template<class QElemType> 96 SqQueue<QElemType>::SqQueue(const SqQueue<QElemType> &q) 97 { 98 base = new QElemType[MAXQSIZE]; 99 front = q.front; 100 rear = q.rear; 101 102 for(int i=0; i<MAXQSIZE; i++)//複製整個陣列 103 { 104 base[i]=q.base[i]; 105 } 106 }Queue Class node
3、Link
1 /***鏈隊的基本操作***/ 2 3 #define OK 1 4 #define ERROR 0 5 #define OVERFLOW -2 6 typedef char QElemType; 7 typedef int Status; 8 9 //- - - - - 佇列的鏈式儲存結構- - - - - 10 typedef struct QNode { 11 QElemType data; 12 struct QNode *next; 13 } QNode, *QueuePtr; 14 typedef struct { 15 QueuePtr front; //隊頭指標 16 QueuePtr rear; //隊尾指標 17 } LinkQueue; 18 19 //演算法3.16 鏈隊的初始化 20 Status InitQueue(LinkQueue &Q) {//構造一個空佇列Q 21 Q.front = Q.rear = new QNode; //生成新結點作為頭結點,隊頭和隊尾指標指向此結點 22 Q.front->next = NULL; //頭結點的指標域置空 23 return OK; 24 } 25 26 //演算法3.17 鏈隊的入隊 27 Status EnQueue(LinkQueue &Q, QElemType e) {//插入元素e為Q的新的隊尾元素 28 QueuePtr p; 29 p = new QNode; //為入隊元素分配結點空間,用指標p指向 30 p->data = e; //將新結點資料域置為e 31 p->next = NULL; 32 Q.rear->next = p; //將新結點插入到隊尾 33 Q.rear = p; //修改隊尾指標 34 return OK; 35 } 36 37 //演算法3.18 鏈隊的出隊 38 Status DeQueue(LinkQueue &Q, QElemType &e) {//刪除Q的隊頭元素,用e返回其值 39 QueuePtr p; 40 if (Q.front == Q.rear) 41 return ERROR; //若佇列空,則返回ERROR 42 p = Q.front->next; //p指向隊頭元素 43 e = p->data; //e儲存隊頭元素的值 44 Q.front->next = p->next; //修改頭指標 45 if (Q.rear == p) 46 Q.rear = Q.front; //最後一個元素被刪,隊尾指標指向頭結點 47 delete p; //釋放原隊頭元素的空間 48 return OK; 49 } 50 51 //演算法3.19 取鏈隊的隊頭元素 52 QElemType GetHead(LinkQueue Q) {//返回Q的隊頭元素,不修改隊頭指標 53 if (Q.front != Q.rear) //佇列非空 54 return Q.front->next->data; //返回隊頭元素的值,隊頭指標不變 55 }Queue Link node