栈的链式存储设计与实现
1、栈的链式存储是通过线性表的链式存储来模拟的。在头部添加或删除元素不会涉及到数组元素的大量移动。
2、栈的链式存储思路基本与线性表的链式存储一致,可参考线性表的链式存储。线性表的链式存储
3、相关代码
(1)linkstack.h
#ifndef _MY_LINKSTACK_H_ #define _MY_LINKSTACK_H_ typedef void LinkStack; LinkStack* LinkStack_Create(); void LinkStack_Destory(LinkStack* stack); void LinkStack_Clear(LinkStack* stack); int LinkStack_Push(LinkStack* stack, void* item); void* LinkStack_Pop(LinkStack* stack); void* LinkStack_Top(LinkStack* stack); int LinkStack_Size(LinkStack* stack); #endif
(2)linkstack.c
#include <stdlib.h> #include <stdio.h> #include <string.h> #include "linkstack.h" #include "linklist.h" typedef struct _tag_LinkStackNode //链表业务结点 { LinkListNode node;//第一个域(第一个元素) void* item;//栈的业务结点 }TLinkStackNode; //创建栈 相当于创建一个线性表 LinkStack* LinkStack_Create() { return LinkList_Create(); } //销毁栈相当于销毁一个线性表 //销毁栈的时候会涉及到栈元素生命周期的管理 //因为所有入栈的结点都是malloc出来的,若要清空栈,把栈中的元素弹出,也要释放结点内存 void LinkStack_Destory(LinkStack* stack) { LinkStack_Clear(stack); LinkList_Destory(stack); } //清空栈相当于清空一个线性表 //清空栈的时候会涉及到栈元素生命周期的管理 void LinkStack_Clear(LinkStack* stack) { if (stack == NULL) { return; } while (LinkStack_Size(stack) > 0) { LinkStack_Pop(stack);//在这个函数中已经释放结点内存 } return; } //向栈中压入元素 相当于向线性表的头部插入元素 //void* item栈的业务结点 转化成 链表的业务结点 int LinkStack_Push(LinkStack* stack, void* item) { TLinkStackNode *tmp = NULL; int ret = 0; tmp = (TLinkStackNode *)malloc(sizeof(TLinkStackNode)); if (tmp == NULL) { return -1; } memset(tmp, 0, sizeof(TLinkStackNode)); tmp->item = item; //int LinkList_Insert(LinkList* list, LinkListNode* node, int pos); ret = LinkList_Insert(stack, (LinkListNode*)tmp, 0); if (ret != 0) { printf("func LinkList_Insert() err:%d\n", ret); if (tmp != NULL) { free(tmp); } return ret; } return ret; } //从栈中弹出元素 相当于从线性表的头部删除元素 //把线性表的业务结点 转化成 栈的业务结点 void* LinkStack_Pop(LinkStack* stack) { void *item = NULL;//栈的业务结点 TLinkStackNode* tmp = NULL;//线性表链式存储的业务结点 tmp = (TLinkStackNode*)LinkList_Delete(stack, 0); if (tmp == NULL) { return NULL; } item = tmp->item; //因为LinkList_Insert()的时候分配了内存,所以LinkList_Delete()释放内存 free(tmp); return item; } //获取栈顶元素 相当于获取线性表的0号位置元素 void* LinkStack_Top(LinkStack* stack) { TLinkStackNode* tmp = NULL; tmp = (TLinkStackNode*)LinkList_Get(stack, 0); if (tmp == NULL) { return NULL; } return tmp->item; } //求栈的大小 相当于求线性表的length int LinkStack_Size(LinkStack* stack) { return LinkList_Length(stack); }
(3)具体实现
#include <stdlib.h> #include <stdio.h> #include <string.h> #include "linkstack.h" #include "linklist.h" void maindm007() { int a[10]; //创建栈 LinkStack* lstack = NULL; lstack = LinkStack_Create(); if (lstack == NULL) { return; } //压入元素 for (int i = 0; i < 5; i++) { a[i] = i + 1; LinkStack_Push(lstack, &a[i]); } //打印栈顶元素 printf("The LinkStack's Top:%d \n", *((int*)LinkStack_Top(lstack))); //打印栈的实际长度 printf("The LinkStack's Size:%d \n", LinkStack_Size(lstack)); //删除栈元素 while (LinkStack_Size(lstack) > 0) { int tmp = *((int *)LinkStack_Pop(lstack)); printf("tmp:%d ", tmp); } printf("\n"); //销毁栈 LinkStack_Destory(lstack); /* LinkStack* LinkStack_Create(int capacity); void LinkStack_Destory(LinkStack* stack); void LinkStack_Clear(LinkStack* stack); int LinkStack_Push(LinkStack* stack, void* item); void* LinkStack_Pop(LinkStack* stack); void* LinkStack_Top(LinkStack* stack); int LinkStack_Size(LinkStack* stack); */ system("pause"); return; }