链式栈

来源:互联网 发布:炫浪网络社区 小说阅读 编辑:程序博客网 时间:2024/05/16 18:46

单链表部分

#ifndef __LINKLIST_H__#define __LINKLIST_H__typedef void LinkList;//链表的数据封装 typedef struct _tag_LinkListNode LinkListNode;//指针域的重命名,指针域的定义最重要,在链表中遍历节点的时候就是利用指针域的移动,//他既包含了当前节点的地址信息,由于它是结构体,所以又包含了下一个节点的地址信息; struct  _tag_LinkListNode{//指针域结构体的具体定义 LinkListNode* next;//用指针域定义指针域 };LinkList* LinkList_Create();void LinkList_Destroy(LinkList* list);void LinkList_Clear(LinkList* list);int LinkList_Length(LinkList* list);int LinkList_Insert(LinkList* list,LinkListNode* node,int pos);LinkListNode* LinkList_Delete(LinkList* list,int pos);LinkListNode* LinkList_Get(LinkList* list,int pos);#endif


#include <stdio.h>#include <malloc.h>#include "LinkList.h"typedef struct _tag_LinkList{//表头结构体 LinkListNode header;//表头指针,header是一个结构体,成员是一个指针 int length;//链表长度成员,在这里没有直接定义链表节点成员 }TLinkList; LinkList* LinkList_Create() {TLinkList* ret = (TLinkList*)malloc(sizeof(TLinkList));//动态分配空间,刚刚创建的时候只需要分配表头的空间 if(ret != NULL){ret->length = 0;//对长度初始化为0 ret->header.next = NULL; //对表头指针成员初始化为NULL }return ret;//返回表头地址 }void LinkList_Destroy(LinkList* list){free(list);}void LinkList_Clear(LinkList* list){TLinkList* sList = (TLinkList*)list;if(sList != NULL){//让表头恢复到刚刚创建的状态 sList->length = 0;sList->header.next = NULL;}}int LinkList_Length(LinkList* list){TLinkList* sList = (TLinkList*)list;//除了destroy函数,其余函数基本上都会用到强制类型转换 int ret = -1;if(sList != NULL){//如果合法则返回当前长度 ret = sList->length; } return ret;}int LinkList_Insert(LinkList* list,LinkListNode* node,int pos){TLinkList* sList = (TLinkList*)list;//强制类型转换 int ret = (sList != NULL)&&(pos >= 0)&&(node != NULL);//合法性检测 int i = 0;if(ret){LinkListNode* current = (LinkListNode*)sList;//将表头指针强制转换为当前指针。结构体指针指向结构体中的第一个成员 for(i = 0;(i < pos) && (current->next != NULL);i++){//移动当前指针,使得当前指针的指针域指向的元素的位置即要插入新元素的位置 current = current->next;}node->next = current->next;//将当前指针指向的下一个元素的位置赋值给要插入的节点的指针域 current->next = node;//将要插入的节点的位置赋值给当前指针的指针域 sList->length++;//更新长度 } return ret;//成功插入返回1否则返回0 }LinkListNode* LinkList_Get(LinkList* list,int pos){TLinkList* sList = (TLinkList*)list;LinkListNode* ret  = NULL;int i = 0;if((sList != NULL) && (pos >= 0) && (pos < sList->length)){//合法性检测 LinkListNode* current = (LinkListNode*)sList;//将表头指针赋值为当前指针 for(i = 0; i < pos;i++){//移动当前指针使得它的指针域指向要获取的节点 current = current->next;} ret = current->next;//返回获取的节点 } return ret;//返回的是结构体的指针,即结构体的地址 }LinkListNode* LinkList_Delete(LinkList* list,int pos){TLinkList* sList = (TLinkList*)list;LinkListNode* ret  = NULL;int i = 0;if((sList != NULL) && (pos >= 0) && (pos < sList->length)){LinkListNode* current = (LinkListNode*)sList;for(i = 0; i < pos;i++){current = current->next;}ret = current->next;current->next = ret->next;//将当前指针的指针域指向要删除的节点的指针域,即可删除节点 sList->length--;//更新长度成员 }return ret;}


链式栈部分

#ifndef __LINKSTACK_H__ #define __LINKSTACK_H__typedef void LinkStack;LinkStack* LinkStack_Create();void LinkStack_Destroy(LinkStack* stack);void LinkStack_Clear(LinkStack* stack);int LinkStack_Size(LinkStack* stack);int LinkStack_Push(LinkStack* stack,void* item);void* LinkStack_Pop(LinkStack* stack);void* LinkStack_Top(LinkStack* stack);#endif


#include <malloc.h>#include "LinkList.h"#include "LinkStack.h"typedef struct _tag_LinkStackNode{//定义栈里面每个数据元素的结构体 LinkListNode header;//为了和单链表的节点匹配 void* item;//实际的存放数据的成员(实际上存放的是数据在内存中的地址) }TLinkStackNode;LinkStack* LinkStack_Create(){return LinkList_Create();}void LinkStack_Destroy(LinkStack* stack){LinkStack_Clear(stack);//由于每一次插入都有申请空间的操作,所以不能直接free,应该将在建立栈以后申请的空间逐一清空再free LinkList_Destroy(stack);//当栈里面没有数据以后就可以释放申请的空间 }void LinkStack_Clear(LinkStack* stack)//将所有数据弹出栈 {while(LinkStack_Size(stack) > 0){//通过判断栈的大小来确定是否还有数据存在 LinkStack_Pop(stack);}}int LinkStack_Size(LinkStack* stack){return LinkList_Length(stack);}int LinkStack_Push(LinkStack* stack,void* item){TLinkStackNode* node = (TLinkStackNode*)malloc(sizeof(TLinkStackNode));//每次新数据进栈都要重新为其申请空间 int ret = (stack != NULL) && (node != NULL) && (item != NULL);//合法性检测 if(ret){node->item = item;//将要进栈的数据传递给申请出来的新空间的item成员 ret = LinkList_Insert(stack,(LinkListNode*)node,0);//头插法链表的头部是栈顶 }if(!ret){//如果进栈没有成功则要把之前为之申请的空间释放 free(node);}return ret;//成功返回1否则返回0 }void* LinkStack_Pop(LinkStack* stack){TLinkStackNode* node = (TLinkStackNode*)LinkList_Delete(stack,0);//将栈顶元素弹出,实际上就是删除链表的第一个节点 void* ret = NULL;if(node != NULL){ret = node->item;//返回栈顶元素的数据成员(存放数据的地址) }return ret;}void* LinkStack_Top(LinkStack* stack){TLinkStackNode* node = (TLinkStackNode*)LinkList_Get(stack,0);//获取栈顶元素 void* ret = NULL;if(node != NULL){ret = node->item;}return ret;}


测试程序

#include <stdio.h>#include <stdlib.h>#include "LinkStack.h"/* run this program using the console pauser or add your own getch, system("pause") or input loop */int main(int argc, char *argv[]) {    LinkStack* stack = LinkStack_Create();    int a[10];    int i = 0;        for(i=0; i<10; i++)    {        a[i] = i;                LinkStack_Push(stack, a + i);    }        printf("Top: %d\n", *(int*)LinkStack_Top(stack));    printf("Length: %d\n", LinkStack_Size(stack));        while( LinkStack_Size(stack) > 0 )    {        printf("Pop: %d\n", *(int*)LinkStack_Pop(stack));    }        LinkStack_Destroy(stack);    return 0;}


0 0
原创粉丝点击