六、C语言实现栈的基本功能

六、C语言实现栈的基本功能

1、栈的原则:

先进后出,后进先出

在这里插入图片描述
2、声明

#pragma once

//结构声明
typedef int Element;

typedef struct Stack
{
	int size;            //栈容量
	int top;             //栈顶下标
	Element* stack_low;  //栈底指针
}Stack,*PStack;          //PStack可用来定义指针类型的栈

//栈扩容
bool ApplyNewSpace(Stack* st);

//初始化栈
void InitStack(Stack* st, int init_size);

//判栈满
bool StackIsFull(Stack* st);

//判空
bool StackIsEmpty(Stack* st);

//入栈
void PushStack(Stack* st, Element value);

//出栈
void PopStack(Stack* st);

//求栈顶元素
Element TopElem(Stack* st, Element* reval);

//销毁栈
void DestroyStack(Stack* st);

//输出栈中元素
void ShowStack(Stack* st);

//栈功能测试
void StackTest(void);

3、方法实现

#include "Stack.h"
#include <stdlib.h>
#include <malloc.h>
#include <stdio.h>

//栈扩容
bool ApplyNewSpace(Stack* st)
{
	if (st == NULL)  return false;

	//栈里的数据类型是Element
	Element* newspace = (Element*)malloc(sizeof(Element) * st->size * 2);
	if (newspace == NULL) return false;

	//转移数据
	for (int i = 0; i < st->size; i++)
	{
		newspace[i] = st->stack_low[i];
	}

	free(st->stack_low);
	st->stack_low = newspace;
	st->size *= 2;
}

//初始化栈
void InitStack(Stack* st, int init_size)
{

	if (st == NULL) exit(0);
	init_size = init_size > 0 ? init_size : 10;

	st->stack_low = (Element*)malloc(sizeof(Element)*init_size);
	if (st->stack_low == NULL) exit(0);

	st->top = 0;
	st->size = init_size;

}
//判栈满
bool StackIsFull(Stack* st)
{
	if (st == NULL) exit(0);

	return st->size == st->top;
}


//判空
bool StackIsEmpty(Stack* st)
{
	if (st == NULL) exit(0);

	return st->top == 0;
}

//入栈
void PushStack(Stack *st, Element value)
{
	if (st == NULL) exit(0);
	if (StackIsFull(st)&& !ApplyNewSpace(st))  exit(0);

	st->stack_low[st->top++] = value;
}

//出栈
void PopStack(Stack* st)
{
	if (st == NULL) exit(0);
	if (StackIsEmpty(st)) exit(0);
	
	st->top--;
}

//求栈顶元素
Element TopElem(Stack *st,Element *reval)
{
	if (st == NULL) exit(0);
	if (StackIsEmpty(st)) exit(0);

	*reval = st->stack_low[st->top-1];
	
	return *reval;
}

//销毁栈
void DestroyStack(Stack* st)
{
	if (st == NULL) exit(0);
	//栈中元素的数据值可以不做处理

	free(st->stack_low);
	st->stack_low = NULL;
	st->size = 0;
	st->top = 0;
}

//输出栈中元素
void ShowStack(Stack* st)
{
	if (st == NULL) exit(0);

	while (!StackIsEmpty(st))
	{
		Element tmp = 0;
		printf("%d ", TopElem(st, &tmp));
		PopStack(st);
	}
	printf("\n");
}


//栈功能测试
void StackTest(void)
{
	Stack st;
	InitStack(&st, 10);
	printf("入栈:13 56 28 77 12 42 78 32 66 42 29\n");
	PushStack(&st, 13);
	PushStack(&st, 56);
	PushStack(&st, 28);
	PushStack(&st, 77);
	PushStack(&st, 12);
	PushStack(&st, 42);
	PushStack(&st, 78);
	PushStack(&st, 32);
	PushStack(&st, 66);
	PushStack(&st, 42);
	PushStack(&st, 29);
	printf("出栈:");

	//ShowStack中有Pop有Stack操作
	ShowStack(&st);

	DestroyStack(&st);

	
}

4、主函数测试

#include "Stack.h"

int main()
{
	StackTest();
	return 0;
}

5、测试结果
在这里插入图片描述
6、注意事项

栈空间结构体中包含:(int)栈容量大小、(存储数据的类型)栈底指针、以及(int)栈顶top下标

本文中的输出(ShowStack)会Pop掉栈中所有元素,所以要想实现既能够输出,还要保留栈中元素,就得设置flag来保存top下标,输出用top- -来实现,这样就不会Pop掉所有元素。

改后的代码实现如下

//输出栈中元素
void ShowStack(Stack* st)
{
	if (st == NULL) exit(0);

	/*while (!StackIsEmpty(st))
	{
		Element tmp = 0;
		printf("%d ", TopElem(st, &tmp));
		PopStack(st);
	}*/
	int flag = st->top;
	while (st->top > 0)
	{
		printf("%d ", st->stack_low[st->top-1]);
		st->top--;
	}

	st->top = flag;
	printf("\n");
}


//栈功能测试
void StackTest(void)
{
	Stack st;
	InitStack(&st, 10);
	printf("入栈:13 56 28 77 12 47 78 32 66 42 29\n");
	PushStack(&st, 13);
	PushStack(&st, 56);
	PushStack(&st, 28);
	PushStack(&st, 77);
	PushStack(&st, 12);
	PushStack(&st, 47);
	PushStack(&st, 78);
	PushStack(&st, 32);
	PushStack(&st, 66);
	PushStack(&st, 42);
	PushStack(&st, 29);
	printf("出栈:");


	ShowStack(&st);

	printf("\n");
	printf("在执行Pop5次, 出栈的元素为29 42 66 32 78 \n");
	for(int i=0;i<5;i++)
	{
		PopStack(&st);
	}

	printf("出栈为:");
	ShowStack(&st);

	DestroyStack(&st);

	
}

此次结果:
在这里插入图片描述

所以栈作为一种线性得数据结构,就好比是一把钳子,想怎么用,看你自己怎么实现。😉

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值