数据结构与算法之——两栈共享存储空间

其实栈的顺序存储很方便,因为它只在表尾进行操作,不存在普通线性表插入与删除还需要移动元素的情况。同样它也有普通线性表的缺陷,即必须确定数量。然而对于两个相同类型的栈,却可以做到最大限度地利用其开辟的存储空间来进行操作。

         数组有两个端点,两个栈使用这一个数组的存储区域,两个栈有两个栈底,分别为数组的始端和末端。

这样在压栈的时候,是栈顶指针往中间靠拢,当两指针相遇时,则栈满。栈空即top1=-1,top2=n。而栈满则是top1 + 1 == top2;

代码实现:

SqDoubleStack.h

/*两栈共享空间--顺序栈结构 */

#define MAXSIZE 5
typedef int SElemType;
typedef struct
{
	SElemType data[MAXSIZE];
	int top1;	//栈1 栈顶指针
	int top2;	//栈2 栈顶指针
}SqDoubleStack;

#define OK 1
#define ERROR 0
typedef int Status;

Status InitStack(SqDoubleStack *S);	//初始化操作,建立一个空栈S
Status DestroyStack(SqDoubleStack *S);	//栈栈存在,则销毁它
Status ClearStack(SqDoubleStack *S);	//将栈清空
int StackEmpty(SqDoubleStack S,int stackNumber);	//若栈为空,返回true,否则返回false
Status GetTop(SqDoubleStack S,SElemType *e,int stackNumber);	//若栈存在且非空,用e返回S的栈顶元素
Status Push(SqDoubleStack *S,SElemType e,int stackNumber);	//若栈S存在,将新元素e插入栈S中并成为栈顶元素
Status Pop(SqDoubleStack *S,SElemType *e,int stackNumber);	//删除栈S中栈顶元素,并用e返回其值
int StackLength(SqDoubleStack S,int stackNumber);	//返回栈S的长度

SqDoubleStack.c

#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include "SqDoubleStack.h"

int main(void)
{
	SqDoubleStack S;
	InitStack(&S);
	printf("已初始化好,现在压栈1,2,3,4");
	Push(&S,1,1);
	Push(&S,2,1);
	Push(&S,3,2);
	Push(&S,4,2);
	Push(&S,5,2);
	printf("\n现在栈1的长度是:%d,栈2的长度是%d\n",StackLength(S,1),StackLength(S,2));
	printf("现在依次弹栈:");
	SElemType e ;
	Pop(&S,&e,1);
	printf("%d,",e);
	Pop(&S,&e,1);
	printf("%d,",e);
	Pop(&S,&e,2);
	printf("%d,",e);
	Pop(&S,&e,2);
	printf("%d,",e);
	Pop(&S,&e,2);
	printf("%d,",e);
	printf("\n现在栈1的长度是:%d,栈2的长度是%d\n",StackLength(S,1),StackLength(S,2));
	return 0;
}

Status InitStack(SqDoubleStack *S)	//初始化操作,建立一个空栈S
{
	memset(S->data,0,sizeof(SElemType)*MAXSIZE);//数组各元素初始化为0
	S->top1 = -1;
	S->top2 = MAXSIZE;
	return OK;
}
Status DestroyStack(SqDoubleStack *S)	//栈栈存在,则销毁它
{
	//free(S);
	return OK;
}
Status ClearStack(SqDoubleStack *S)	//将栈清空
{
	memset(S->data,0,sizeof(SElemType)*MAXSIZE);
	S->top1 = -1;
	S->top2 = MAXSIZE;
	return OK;
}
int StackEmpty(SqDoubleStack S,int stackNumber)	//若栈为空,返回true,否则返回false
{
	if(1==stackNumber)
	{
		return S.top1 == -1;
	}
	else if(2==stackNumber)
	{
		return S.top2 == MAXSIZE;
	}
	return 0;
}
Status GetTop(SqDoubleStack S,SElemType *e,int stackNumber)	//若栈存在且非空,用e返回S的栈顶元素
{
	if(1==stackNumber)
	{
		if(StackEmpty(S,1))
		{
			return ERROR;
		}
		*e = S.data[S.top1];
		return OK;

	}
	else if(2==stackNumber)
	{
		if(StackEmpty(S,2))
		{
			return ERROR;
		}
		*e = S.data[S.top2];
		return OK;
	}
	return ERROR;
}
Status Push(SqDoubleStack *S,SElemType e,int stackNumber)	//若栈S存在,将新元素e插入栈S中并成为栈顶元素
{
	if(S->top1 +1  == S->top2)
	{
		return ERROR;//已满
	}
	if(1==stackNumber)
	{
		S->top1++;
		S->data[S->top1] = e;
		return OK;
	}
	else if(2==stackNumber)
	{
		S->top2--;
		S->data[S->top2] = e;
		return OK;
	}
	return ERROR;
}
Status Pop(SqDoubleStack *S,SElemType *e,int stackNumber)	//删除栈S中栈顶元素,并用e返回其值
{
	if(StackEmpty(*S,stackNumber))
	{
		return ERROR;//为空
	}
	if(1==stackNumber)
	{
		*e = S->data[S->top1];
		S->top1--;
		return OK;

	}
	else if(2==stackNumber)
	{
		*e = S->data[S->top2];
		S->top2++;
		return OK;
	}
	return ERROR;
}
int StackLength(SqDoubleStack S,int stackNumber)	//返回栈S的长度
{	
	if(1==stackNumber)
	{
		return S.top1+1;
	}
	else if(2==stackNumber)
	{
		return MAXSIZE-S.top2;
	}
	return -1;
}

事实上,使用这样的数据结构,通常都是当两个栈的空间需求有相反关系时,也即一个栈增长时,另一个栈在缩短。这样使用两栈共享空间存储方法才有比较大的意义,否则两个栈都在不停地增长,那很快就会有栈满而溢出。

  • 3
    点赞
  • 14
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值