tips:前些天學習了單鏈表的增刪改查,對於雙向鏈表和回圈鏈表而言,無非就是對單鏈表的指針進行稍微的變換。今天來看看c語言數據結構之棧的實現以及棧的各種操作。
棧的特點是先進後出,後進先出,因此我們很容易聯想到去使用單鏈表的頭插法,和頭部刪除法去實現入棧和出棧的操作。
typedef struct tag
{
int val;//棧(鏈表)的值,即數據域部分
struct tag *pNext;//後繼指針
}Node,*pNode;
typedef struct tagStack
{
pNode phead;//鏈表(tag)的頭指針
int size;//棧的大小(棧中元素個數)
}Stack,*pStack;
//列印棧元素
void print_stack(pStack p)
{
pNode pcur = p->phead;//工具人儲存當前結點資訊
while (pcur!=NULL)
{
printf("%d\n",pcur->val);
pcur = pcur->pNext;
}
printf("---------------------------------\n");
}
1、入棧(push)
思路:
具體實現:
//入棧
void push(pStack p, int val)
{
pNode pnew = (pNode)malloc(sizeof(Node));//申請新結點空間(申請的是tag)
//新結點初始化
pnew->val = val;
pnew->pNext = NULL;
//入棧,頭插法
if (p->phead == NULL)//判斷鏈表是否爲空,爲空,頭指針指向新結點
{
p->phead = pnew;
}
else //不爲空,則頭插法
{
//新結點變成新的頭結點
pnew->pNext = p->phead;
p->phead = pnew;
}
p->size++;
}
2、出棧(pop)
思路:
具體實現:
//出棧,頭部刪除法
void pop(pStack p)
{
pNode pcur = p->phead;//工具人儲存當前結點資訊
//判斷鏈表是否爲空
if (p->phead == NULL)
{
printf("該鏈表爲空!\n");
}
else
{
//頭部刪除法
p->phead = pcur->pNext;
free(pcur);
p->size--;
}
}
3、返回棧頂元素(top)
思路:
具體實現:
//返回棧頂元素
int top(pStack p)
{
//判斷鏈表是否爲空
if (p->phead == NULL)
{
return EOF;
}
else
{
//返回棧頂元素
return p->phead->val;
}
}
4、判斷棧是否爲空(empty)
思路:
總之判斷方法很多,大家可以盡情發揮。
具體實現:
//判斷棧是否爲空
int empty(pStack p)
{
//判斷鏈表是否爲空
if (p->phead == NULL)
{
return 0;
}
else
{
return 1;
}
}
5、返回棧中元素個數(size)
思路:
這個實現方法很多,大家可以盡情發揮。
具體實現:
//返回棧中元素個數
int size(pStack p)
{
//判斷鏈表是否爲空
if (p->phead == NULL)
{
return 0;
}
else
{
return p->size;
}
}
至此棧的基本操作我們已經全部實現了,接下來我們在main()函數中測試一下:
int main()
{
//棧的操作,鏈表實現棧stack
Stack s;//定義一個棧
int i;//入棧的值
char panduan;//用來判斷是否彈棧
//使用memset初始化結點(棧)
memset(&s, 0, sizeof(Stack));//棧的初始化,初始化爲0
while (scanf("%d", &i) != EOF)
{
//入棧
push(&s, i);
}
//列印棧元素
printf("棧裏面元素爲:\n");
print_stack(&s);
//列印棧頂元素
printf("棧頂元素爲:%d\n", top(&s));
//判斷棧是否爲空
if (empty(&s))
{
printf("棧不爲空!\n");
}
else
{
printf("棧爲空!\n");
}
//棧中元素個數
printf("棧中元素個數爲:%d\n", size(&s));
printf("---------------------------------\n");
while (printf("是否彈棧?y/n:"),scanf("%c", &panduan) != NULL)
{
if (panduan == 'y')
{
//出棧
pop(&s);
//列印棧元素
print_stack(&s);
//列印棧頂元素
printf("棧頂元素爲:%d\n", top(&s));
//判斷棧是否爲空
if (empty(&s))
{
printf("棧不爲空!\n");
}
else
{
printf("棧爲空!\n");
}
//棧中元素個數
printf("棧中元素個數爲:%d\n", size(&s));
printf("---------------------------------\n");
}
else if(panduan == 'n')
{
break;
}
}
return 0;
}
實現結果:
棧的操作到目前來說已經實現,希望對大家學習有所幫助,加油!
tips:瞄準天上的星星,或許你永遠也射不到,但卻比你瞄準樹梢射得高遠。