数据结构代码复习总结

//----- 1.顺序表的存储结构-----------------------------------------------
#define MAXSIZE 100             //顺序表可能达到的最大长度
    typedef struct {
        ElemType *elem;         //存储空间的基地址
        int length;             //当前长度
    } SqList;                   //顺序表的结构类型为SqList


//----------------------------
//一、顺序表初始化
//①、为顺序表L动态分配一个预定义大小的数组空间,使elem指向这段空间的基地址。
//②、将表的当前长度设为0。

    Status InitList(SqList &L) {
        //构造一个空的顺序表 L
        L.elem = new ElemType[MAXSIZE];     //为顺序表分配一个大小为MAXSIZE的数组空间
        if (!L.elem) exit(OVERFLOW);        //存储分配失败退出
        L.length = O;                       //空表长度为0
        return OK;
    }

//----------------------------
//二、顺序表取值
//①、判断指定的位置序号 i 值是否合理 (1≤i≤L.length), 若不合理,则返回ERROR。
//②、若 i 值合理,则将第 i 个数据元素 L.elem[i-1] 赋给参数 e, 通过 e返回第 i 个数据元素的传值。
    Status GetElem(SqList L, int i, ElemType &e) {
        if {
            (i < 1 || i > L.length) return ERROR;      //判断l. 值是否合理,若不合理, 返回 ERROR
            e = L.elem[i - 1];                         //elem[i-1] 单元存储第 i 个数据元素
            return OK;
        }

    }

//----------------------------
//三、顺序表的按值查找
//①、从第一个元素起,依次和 e相比较,若找到与 e相等的元素 L.elem[i], 则查找成功,返回该元素的序号 i+l (数组下标从 0 开始)
//②、若查遍整个顺序表都没有找到,则查找失败, 返回0
int LocateELem(SqList L, ElemType e) {
        //在顺序表1中查找值为e的数据元素, 返回其序号
        for (i = O; i < L.length; i++) {
            if (L.elem[i)==e){
                return i + l;           //查找成功, 返回序号 i+l
            }
        }
        return O;                       //查找失败, 返回 0           
    }

//----------------------------
//四、顺序表插入元素
//在第 i 个位置插入一个元素时,需从最后一个元素即第 n 个元素开始,依次向后移动一个位置,直至第 i 个元素。
//①、判断插入位置 i 是否合法(i 值的合法范围是 1≤i≤n+ I), 若不合法 则返回 ERROR。
//②、判断顺序表的存储空间是否已满,若满则返回 ERROR。
//③、将第n个至第 i 个位置的元素依次向后移动一个位置,空出第 i 个位置 ( i =n+l 时无需移动)。
//④、将要插入的新元素e放入第i个位置。
//⑤、表长加1
Status Listinsert(SqList &L, int i, ElemType e) {
        //在顺序表 L 中第 i 个位置之前插入新的元素 e, i值的合法范围是 1...i...L.length+l
        if ((i < l) || (i > L.length + l)) {
            return ERROR;                       //i值不合法
        }
        if (L.length == MAXSIZE) {
            return ERROR;                       //当前存储空间已满
        }
        for (j = L.length - 1; j >= i - 1; j--) {
            L.elem[j + l] = L.elem[j];                     //插入位置及之后的元素后移
        }
        L.elem[i - l] = e;                                //将新元素e放入第l个位置
        ++L.length;                                       //表长加1
        return OK;
    }

//----------------------------
//五、顺序表删除元素
//删除第 i 个元素时需将第 i+ 1 个至第 n 个元素依次向前移动一个位置 (i = n 时无需移动)
//①、判断删除位置 i 是否合法(合法值为 1 ≤ i ≤n), 若不合法则返回 ERROR。
//②、将第 i个至第n个的元素依次向前移动一个位置 (i = n时无需移动)
//③、表长减 1
Status ListDelete(SqList &L, int i) {
        //在顺序表L中删除第J.个元素,J.值的合法范围是 1.;;i.;;L. length
            if ((i < l) || (i > L.length)) {
                return ERROR;                               //i值不合法
            }
            for (j = i; j <= L.length - 1; j++) {
                L.elem[j - 1]=1.elem[j];                    //被删除元素之后的元素前移
            }
            --L.length;                                     //表长减 1
            return OK;
        }

//----- 2.单链表的存储结构-----------------------------------------------
    typedef struct LNode {
        ElemType data;          //结点的数据域
        struct LNode *next;     //结点的指针域
    } LNode, *LinkList;         //LinkList 为指向结构体 LNode 的指针类型

//----------------------------
//一、单链表的初始化
//①、生成新结点作为头结点,用头指针L 指向头结点。
//②、头结点的指针域置空。
 Status InitList(LinkList &L) {	 //构造一个空的单链表L
        L = new LNode;        	 //生成新结点作为头结点,用头指针L指向头结点
        L->next = NULL;          //头结点的指针域置空
        return OK;
    }

//----------------------------
//二、单链表的取值
//①、用指针p指向首元结点,用 j 做计数器初值赋为1
//②、从首元结点开始依次顺着链域 next 向下访问,只要指向当前结点的指针 p 不为空(NULL), 并且没有到达序号为 i 的结点,则循环执行以下操作:
//.p指向下一个结点;
//.计数器 j 相应加 1
//③、退出循环时, 如果指针p为空, 或者计数器 j 大于 i, 说明指定的序号 i 值不合法(i 大于表长n或 i 小于等于0), 取值失败返回ERROR; 否则取值成功, 此时 j=i 时,p所指的结点就是要找的第 i 个结点,用参数 e 保存当前结点的数据域, 返回OK。
    Status GetElem(LinkList L, int i, ElemType &e) {
        //在带头结点的单链表L中根据序号l.获取元素的值,用e返回L中第l.个数据元素的值
        p = L->next;
        j = 1;                              //初始化,p指向首元结点,计数器]初值赋为1
        while (p && j < i) {                //顺链域向后扫描,直到p为空或p指向第l.个元素
            p = p->next;                    //p指向下一个结点
            ++j;                            //计数器j相应加1
        }

        if (!p || j > i) return ERROR;      // i值不合法 i>n或i≤0
        e = p->data;                        //取第i个结点的数据域
        return OK;
    }


//----------------------------
//三、单链表的按值查找
//①、用指针p指向首元结点
//②、从首元结点开始依次顺着链域next向下查找, 只要指向当前结点的指针p不为空, 并且p所指结点的数据域不等于给定值e, 则循环执行以下操作: p指向下一个结点 。
//③、返回p。若查找成功,p此时即为结点的地址值,若查找失败,p的值即为NULL
    LNode *LocateELem(LinkList L, Elemtype e) {
        //在带头结点的单链表L中查找值为e的元素
        p = L->next;                            //初始化,p指向首元结点
        while (p && p->data != e) {             //顺链域向后扫描,直到p为空或p所指结点的数据域等于e	
            p = p->next;                        //p指向下一个结点
        }
        return p;                               //查找成功返回值为e的结点地址p, 查找失败p为NULL
    }


//----------------------------
//四、单链表的插入
//将值为e的新结点插入到表的第 i 个结点的位置上,即插入到结点 ai-1与ai之间。
//①、查找结点 ai-1 并由指针p指向该结点
//②、生成一个新结点*s
//③、将新结点*s 的数据域置为 e
//④、将新结点*s 的指针域指向结点ai
//⑤、将结点 * p 的指针域指向新结点*s
 Status Listinsert(LinkList &L, int i, ElemType e) {
        //在带头结点的单链表L中第i个位置插入值为e的新结点
        p = L;
        j = O;
        while (p && (j < i - 1)) {
            p = p->next;
            ++j;                                //查找到第i-1个结点,p指向该结点
        }
        if (!p || j > i - 1) return ERROR;      //i>n+1 或者 i≤1

        s = new LNode;                          //生成新结点 *s

        s->data = e;                            //将结点*s的数据域置为e

        s->next = p->next;                      //将结点 *s的指针域指向结点 ai

        p->next = s;                            //将结点*p的指针域指向结点*s

        return OK;
    }

//----------------------------
//五、单链表的删除
//删除单链表的第 i 个结点ai
//①、查找结点ai-1 并由指针p指向该结点
//②、临时保存待删除结点 ai 的地址在q中 ,以备释放。
//③、将结点*p的指针域指向 ai 的直接后继结点
//④、释放结点ai的空间
    Status ListDelete(LinkList &L, int i) {
//在带头结点的单链表L中,删除第l个元素
        p = L;
        j = O;
        while ((p->next) && (j < i - 1)) {              //查找第i-1个结点,p指向该结点
            p = p->next;
            ++j;
        }
        if (!(p->next) || (j > i - 1)) return ERROR;    //当i>n或i<1时,删除位置不合理
        q = p->next;                                    //临时保存被删结点的地址以备释放
        p->next = q->next;                              //改变删除结点前驱结点的指针域
        delete q;                                       //释放删除结点的空间
        return OK;
    }

//----------------------------
//六、创建单链表
//前插法:始终让新结点在第一的位置,不常用,因为输入顺序和输出顺序是相反的。
//后插法:尾指针r始终指向单链表的表尾,常用(输入顺序和输出顺序相同)

//逆位序输入n个元素的值,建立带表头节点的单链表L
	void CreateList_H(LinkList &L,int n){
		L = new LNode;
		L->next = null;					//建立一个带表头的节点空链表
		for(i=0;i<n;++i){
			p = new LNode;			//生成新节点
			cin>>p->data;			//输入元素值赋给新节点*p的数据域
			p->next = L->next;
			L->next = p;			//将新节点*p插入到头结点之后
		}	
	}
//----------------------------
//正位序输入n个元素的值,建立带表头节点的单链表L--------------
//①、创建一个只有头结点的空链表。
//②、尾指针r初始化, 指向头结点。
//③、根据创建链表包括的元素个数n, 循环n次执行以下操作
//.生成一个新结点*p;
//.输入元素值赋给新结点*p 的数据域;
//.将新结点p 插入到尾结点r之后;
//.尾指针r指向新的尾结点*p

	void CreateList_R(LinkList &L,int n){	
		L = new LNode;
		L->next = null;					//建立一个带表头的节点空链表
		r = L;						//尾指针R指向头结点
		for(i=0;i<n;++i){
			p = new LNode;			//生成新节点
			cin>>p->data;			//输入元素值赋给新节点*p的数据域
			p->next = L->next;
			L->next = p;			//将新节点*p插入到头结点之后
			r = p;
		}	
	}

//----- 3.双向链表的存储结构-----------------------------------------------
	typedef struct DuLNode{
		ElemType data;				//数据域
		struct DuLNode *prior;		//直接前驱
		struct DuLNode *next;		//直接后继
	}DuLNode,*DuLinkList;


//----------------------------	
//一.双向链表的插入
//在带头结点的双向链表L中第i个外置之前插入元素e
	Status ListInsert_DuL(DuLinkList &L,int i,ElemType e){
		if(!(p=GetElem_DuL(L,i))){		//在L中确定第i个元素的位置指针p
			return ERROR;				//p为NULL时,第i个元素不存在
		}else{
			s = new DuLNode; 			//生成新节点
			s->data = e;				//将节点*s数据域置为e
			s->prior = p->prior;		//将节点*s插入L中
			p->prior->next = s;			
			s->next = p;
			p->prior = s;
			return ok;
		}
	}

	
//二.双向链表的删除
//删除带头结点的双向链表L中第i个元素
	Status ListInsert_DuL(DuLinkList &L,int i,ElemType e){
		if(!(p=GetElem_DuL(L,i))){		//在L中确定第i个元素的位置指针p
			return ERROR;				//p为NULL时,第i个元素不存在
		}else{
			p->prior->next =  p->next;		//删除被删节点的前驱节点的后继指针
			p->next->prior =  p->prior;		//修改被删节点的后继节点的前驱指针
			delete p;						//释放被删节点的空间
			return ok;
		}
	}

//----- 4.顺序栈的存储结构-----------------------------------------------
#define MAXSIZE 100 		//顺序栈存储空间的初始分配址
    typedef struct{
        SElemType *base; 		//栈底指针
	    SElemType *top; 		//栈顶指针
	    int stacksize; 			//栈可用的最大容扯
    }SqStack;

//栈的初始化
Status InitStack(sqStack *s) {
    s->base = new ElemType[MAXSIZE];
    if (!s->base) {
        exit(OVERFLOW);
    }
    s->top = s->base;
    s->stackSize = MAXSIZE;
    return OK;
}

//入栈
Status Push(sqStack *s, ElemType e) {
    if (s->top - s->base == s->stackSize) {
        return ERROR;
    }
    *(s->top) = e;
    s->top++;
    return OK;
}

//出栈
Status Pop(sqStack *s, ElemType *e) {
    if (s->top == s->base) {
        return ERROR;
    }
    *e = *--(s->top);
    return OK;
}

//取栈顶元素
SElemType GetTop(sqStack S) {
    if(S.top != S.base)
        return *(S.top-1);
}

//返回栈的容量
Status StackLen(sqStack s) {
    return (s.top - s.base);
    //不是地址的相减而是内容
}

//----- 4.链栈的存储结构-----------------------------------------------
typedef struct StackNode{
    ElemType data;
    struct StackNode *next;
}StackNode,*LinkStack;

//初始化栈
Status InitStack(LinkStack &S) {
    S = NULL;
    return OK;
}

//入栈
Status Push(LinkStack &S,SElemType e) {    //在栈顶插入e
   
    p = new StackNode;        //生成新节点
    p->data = e;              //将新节点数据域置为e
    p->next = S;              //将新节点插入栈顶
    S = p;                    //修改栈顶指针为p
    return OK;
}

//出栈
Status Pop(LinkStack &S,SElemType e) {    //删除S栈顶元素,用e返回其值
    if (S == NULL) {
        return ERROR;        //栈空
    }
    e = S->data;            //将栈顶元素赋值给e
    p = S;                   //用p临时保存栈顶元素空间,以备释放
    S = S->next;             //修改栈顶指针
    delete p;                //释放原栈顶元素的空间
    return OK;
}

//取栈顶元素
SElemType GetTop(LinkStack S) {    //返回S的栈顶元素,不修改栈顶指针
    if(S != NULL){
        return S->data;
    }
}

//----- 5.队列的顺序存储结构-----------------------------------------------
#define MAXSIZE 100
typedef int QelemType;
typedef struct {
    QelemType *base;        //存储空间的基地址
    int front;            //头指针
    int rear;             //尾指针
} sqQueue;

//循环队列的初始化
Status InitQuene(sqQueue &Q) {
    Q.base = new QelemType[MAXSIZE];    //为队列分配一个最大容量为MAXSIZE的数组空间
    if (!Q.base) {
        exit(OVERFLOW);                //存储分配失败
    }
    Q.front = Q.rear = 0;               //头指针和尾指针为0,队列为空
    return OK;
}

//入队
Status EnQuene(sqQueue &Q, QelemType e) {        //插入元素e为Q的新的队尾元素
    if ((Q.rear + 1) % MAXSIZE == Q.front) {    //尾指针在循环意义上加1后等于头指针,表明对满
        return ERROR;
    }
    Q.base[Q.rear] = e;                        //新元素插入队尾
    Q.rear = (Q.rear + 1) % MAXSIZE;            //队尾指针加1
    return OK;
}

//出队
Status DeQuene(sqQueue &Q, QelemType e) {        //删除Q的对头元素,用e返回其值
    if (Q.rear == Q.front) {                //队空
         return ERROR;
    }
    e = Q.base[Q.front];                    //保存队头元素
    Q.front = (Q.front + 1) % MAXSIZE;        //队头指针加1
    return OK;
}

//去队头元素
SElemType GetHead(SqQueue Q){
    if(Q.front != Q.rear)            //队列非空
        return Q.base[Q.front];        //返回队头元素的值,队头指针不变
}

//循环队列的长度
int QueueLength(sqQueue s) {
    return (s.rear - s.front + MAXSIZE) % MAXSIZE;        //
}


//----- 5.队列的链式存储结构-----------------------------------------------
typedef struct QNode {
    QElemType data;
    struct QNode *next;
} QNode, *QueuePtr;  //一个结点变量,一个指针变量,pointer缩写Ptr

typedef struct {
    QueuePtr front;  //队头指针
    QueuePtr rear;  //队尾指针
} LinkQueue;

//初始化链队
bool InitQueue(LinkQueue &Q) {
    Q.front = Q.rear = new QNode;
    Q.front->next = NULL; //头结点指针域置空
    return OK;
}

//链队销毁
bool DestoryQueue(LinkQueue &Q) {
    while (Q.front) {
        QNode *p = Q.front->next;
        delete Q.front;
        Q.front = p;//或者写Q.rear=Q.front0->next;free(Q.front);Q.front=Q.rear;
    }
    return true;
}

//链队的入队
Status EnQueue(LinkQueue &Q, QElemType e) {
    p = new QNode;            //指针p指向为入队元素分配的结点空间
    p->data = e;               //将新节点数据域置为e 
    p->next = NULL;
    Q.rear->next = p;        //将新节点插入到队尾
    Q.rear = p;             //修改队尾指针
    return OK;
}

//链队的出队
bool DeQueue(LinkQueue &Q, QElemType &e) {
    if (Q.front == Q.rear)
        return ERROR;
    p = Q.front->next;            //p指向队头元素
    e = p->data;
    Q.front->next = p->next;       //修改头指针
    if (Q.rear == p)
        Q.rear = Q.front;        //头结点下一结点就是尾结点时
    delete p;
    return true;
}

//取队头
int GetHead(LinkQueue Q) {
    if (Q.front != Q.rear)    //队列非空
        return Q.front->next->data;    //返回队头元素,队头指针不变
    else {
        return 0;
    }
}

//----- 6.二叉树存储结构-----------------------------------------------
//二叉树的二叉链表存储表示
    typedef struct BiTNode {
        TElemType data;                     //结点数据域
        struct BiTNode *lchild, *rlchild;   //左右孩子指针
    } BiTNode, *BiTree;

//中序遍历递归算法
	void InOrderTraverse(BiTree T){	
		if(T){
			InOrderTraverse(T->lchild);		//左子树
			cout<<T->data;					//根节点
			InOrderTraverse(T->rchild);		//由子树
		}
	}

//中序遍历二叉树T的非递归算法
	void InOrderTraverse(BiTree T){	
		InitStack(S);
		p = T;
		q = new BiTNode;
		while(p||!StackEmpty(S)){
			if(p){					//p存在,非空
				Push(S,p);			//根指针进栈
				p = p->lchild;		//根指针进栈遍历左子数
			}else{
				Pop(S,q);			//p为空,退栈
				cout<<q->data;		//访问根节点
				p = q->rchild;		//遍历右子树
			}
		}
	}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值