在数据结构中,栈是限制在表的一端进行插入和删除的线性表。在线性表中允许插入、删除的这一端称为栈顶,栈顶的当前位置是动态变化的,这样我们只能在栈顶对栈进行操作;不允许插入和删除的另一端称为栈底,栈底是固定不变得,当表中没有元素时称为空栈。
这里我们直接用以前写的单链表来封装栈:
//linklist.h文件
#ifndef __LINKLIST_H__
#define __LINKLIST_H__
typedef struct linklistnode
{
struct linklistnode *next;
int item;
}LinkListNode; //数据节点
typedef struct linklist
{
LinkListNode header;
int length;
}LinkList; //头节点
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_Get(LinkList *list,int pos);
LinkListNode *LinkList_Delete(LinkList *list,int pos);
#endif //__LINKLIST_H__
//linklist.c文件
#include <stdlib.h>
#include "linklist.h"
LinkList *LinkList_Create()
{
LinkList *ret = NULL;
ret = malloc(sizeof(LinkList));
if(ret!=NULL)
{
ret->length = 0;
ret->header.next = NULL;
}
return ret;
}
void LinkList_Destroy(LinkList *list)
{
free(list);
}
void LinkList_Clear(LinkList *list)
{
if(list!=NULL)
{
list->length =0;
list->header.next = NULL;
}
}
int LinkList_Length(LinkList *list)
{
int ret = -1;
if( list!=NULL )
{
ret = list->length;
}
return ret;
}
int LinkList_Insert(LinkList *list, LinkListNode *node, int pos)
{
int ret = list!=NULL && node!=NULL && pos>=0;
if( ret )
{
int i;
LinkListNode *cur = (LinkListNode *)list;
for(i=0;i<pos && cur->next!=NULL;i++)
{
cur = cur->next;
}
node->next = cur->next;
cur->next = node;
list->length++;
}
return ret;
}
LinkListNode *LinkList_Get(LinkList *list,int pos)
{
LinkListNode *ret = NULL;
if( list!=NULL && (0<=pos && pos<list->length) )
{
int i;
LinkListNode *cur = (LinkListNode *)list;
for(i=0; i<pos; i++)
cur = cur->next;
ret = cur->next; //因为从0开始计数的,要第三个数,那么就是第二个数的next
}
return ret;
}
LinkListNode *LinkList_Delete(LinkList *list,int pos)
{
LinkListNode *ret = NULL;
if(list!=NULL && (0<=pos&&pos<list->length) )
{
int i;
LinkListNode *cur = (LinkListNode *)list;
for(i=0; i<pos; i++)
cur = cur->next;
ret = cur->next; //单项链表是从0开始排的。
cur->next = ret->next;
list->length--;
}
return ret;
}
//linkstack.h文件
#ifndef __LINKSTACK_H__
#define __LINKSTACK_H__
typedef struct linkstacknode
{
struct linkstacknode *node;
void *item;
}LinkStackNode;
typedef void LinkStack;
LinkStack *LinkStack_Create();
void LinkStack_Destroy(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 //__LINKSTACK_H__
//linkstack.c文件
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "linklist.h"
#include "linkstack.h"
//栈的创建
LinkStack *LinkStack_Create()
{
return LinkList_Create();
}
void LinkStack_Destroy(LinkStack *stack)
{
LinkStack_Clear(stack);
LinkList_Destroy(stack);
}
//栈的清空
void LinkStack_Clear(LinkStack *stack)
{
while ( LinkStack_Size(stack) > 0 )
LinkStack_Pop(stack);
}
//进栈
int LinkStack_Push(LinkStack *stack,void *item)
{
LinkStackNode *node = malloc(sizeof(LinkStackNode));
int ret = stack!=NULL && item!=NULL && node!=NULL;
if( ret )
{
memset(node,0x00,sizeof(*node)); //??
node->item = item;
ret = LinkList_Insert(stack, (LinkListNode *)node, 0);
}
if(!ret)
{
free(node);
}
return ret;
}
//出栈
void *LinkStack_Pop(LinkStack *stack)
{
LinkStackNode *node = NULL;
void *ret = NULL;
node = (LinkStackNode *)LinkList_Delete(stack,0);
if ( node != NULL)
{
ret = node->item;
free(node);
}
return ret;
}
//栈顶
void *LinkStack_Top(LinkStack *stack)
{
LinkStackNode *node = NULL;
void *ret = NULL;
node = (LinkStackNode *)LinkList_Get(stack,0);
if( node!=NULL)
{
ret = node->item;
}
return ret;
}
//栈的大小
int LinkStack_Size(LinkStack *stack)
{
return LinkList_Length(stack);
}
//main.c文件
#include <stdio.h>
#include <stdlib.h>
#include "linkstack.h"
int main( void )
{
LinkStackNode *stack = LinkStack_Create();
int a[5] = {};
int i;
for(i=0; i<5; i++)
{
a[i] =i+1;
LinkStack_Push(stack, a+i);
}
printf("top:%d\n",*(int *)LinkStack_Top(stack));
printf("size:%d\n",LinkStack_Size(stack));
while( LinkStack_Size(stack)>0 )
{
printf(":%d\n",*(int *)LinkStack_Pop(stack));
}
LinkStack_Destroy(stack);
return 0;
}
//Makefile
cc :=gcc
main : main.o linklist.o linkstack.o
gcc $^ -o $@
.PHONY : main clean
clean:
rm -rf *.o main