#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<iostream>
#define ElemType char
#define Status int
#define StackInitSize 100
//其实也可以写成 typedef int ElemType;
//栈的顺序结构表示
typedef struct
{
ElemType* base;
ElemType* top;
int stacksize;
}seqstack;
//初始化一个顺序栈
Status InitStack(seqstack& s)//传递的是地址
{
s.base = (ElemType*)malloc(StackInitSize * sizeof(ElemType));
if (!s.base)
{
return 0;
}
s.top = s.base;
s.stacksize = StackInitSize;
return 1;
}
//创建栈
Status CreateStack(seqstack &s)//其实不是特别清楚什么时候传递的参数为地址
{
int m = 0;
char n;//n作为接收从键盘中输入的值
printf("请输入元素,若输入完成则输入$:\n");
//getchar();
while (m < StackInitSize)
{
//scanf_s("%c", &n);
n = getchar();
if (n != '$')
{
*s.top = n;//把值放进栈里边,双重指针表非指针,嘿嘿
s.top++;//头结点往上移动
}
else
return 1;
//scanf_s("%c", &n);
//if (n == '$')
// return 1;
//*s.top = n;//将n的值赋给top
//s.top++;//头结点往上移动
m++;
}
}
//判断栈是否为空
Status StackEmpty(seqstack s)
{
if (s.top == s.base)
return 0;
else
return 1;
}
//遍历输出栈内元素
//(因为要对栈进行判空操作,则先写判空)
Status print(seqstack s)
{
ElemType* i;
i = s.top;//服从后进先出的原则
if (StackEmpty(s) == 0)
{
printf("--此栈为空栈--\n");
return 0;
}
while (i > s.base)
{
i--;
printf("%c", *i);
}
printf("\n");
return 1;
}
//进行入栈操作的编写,入栈之前需要进行判满的操作
Status PushStack(seqstack& s, ElemType& e)
{
if (s.top - s.base == 0)//判满
{
printf("--此栈已满--\n");
return 0;
}
else
*s.top++ = e;//把头结点向上移动后,把e的地址作为头结点的地址域
}
//出栈,后进先出,则该元素为栈顶元素
char PopStack(seqstack& s)
{
if (StackEmpty == 0)
{
printf("--此栈为空栈--\n");
return 0;
}
else
{
char e;
s.top--;//因为头结点指向栈顶元素的上一个节点,所以需要下移指向栈顶元素
e = *s.top;// 实际上此元素并没真正删除,仍在S.top中,
//但是如果插入元素,就会被更新,就像是删除了一样
return e;
}
}
//主函数
int main()
{
seqstack s;
InitStack(s);
//printf("%d", InitStack(s));//初始化后,检验初始化是否完成
printf("---创建一个顺序栈---\n");
CreateStack(s);
/*
int a = CreateStack(s);
printf("%d", a);//创建栈后,检验创建是否完成
*/
printf("---此刻栈是否为空?---\n");
if (StackEmpty(s) == 1)
printf("--此栈不为空--\n");
else
printf("--此栈为空栈--\n");
printf("---打印这个顺序栈:---\n");
print(s);
printf("---进行入栈操作---\n");
printf("---请输入要入栈的字母---\n");
getchar();
char a;
scanf_s("%c", &a);
PushStack(s, a);
printf("---打印这个顺序栈:---\n");
print(s);
printf("---进行出栈操作---\n");
char b;
b = PopStack(s);//取栈顶元素
printf("--出栈的元素是%c--\n", b);
printf("---打印这个顺序栈:---\n");
print(s);
return 0;
}
以上为总的代码,对于栈满时存在一些问题待改进
————————————————————————————————————————
以下为代码编写过程,有参考网上大佬的代码
创建栈后报错,在scanf_s处缺少&符号
会执行两遍创建栈?
在主函数里边确实有两个
修改后,基本逻辑没有问题,但是需要输出栈的元素,才能够进一步确定是否成功创建栈
遍历输出栈的元素,首先需要对栈进行判空操作,则首先进行判空
//判断栈是否为空
Status StackEmpty(seqstack s)
{
if (s.top == s.base)
return 0;
else
return 1;
}
//输入栈是否为空
void PrintStackEmpty(seqstack s)
{
if (StackEmpty(s) == 1)
printf("--此栈不为空--\n");
else
printf("--此栈为空栈--\n");
}
本来想在主函数里简单化,但是吧,输出就太简单了
printf("---此刻栈是否为空?---\n");
void PrintStackEmpty(seqstack s);
这是为什么呢?
先检验一下吧,
printf("---此刻栈是否为空?---\n");
if (StackEmpty(s) == 1)
printf("--此栈不为空--\n");
else
printf("--此栈为空栈--\n");
两种情况都为空,emmm,直觉告诉我是在创建栈的时候出现了问题
对比网上资源之后发现,是在传递参数时,别人传的时地址,我传的是结构体,但是吧其实不是特别清楚什么时候传递的参数为地址
修改后,
//创建栈
Status CreateStack(seqstack &s)//其实不是特别清楚什么时候传递的参数为地址
{
int m = 0;
char n;//n作为接收从键盘中输入的值
printf("请输入元素,若输入完成则输入$:\n");
//getchar();
while (m < StackInitSize)
{
//scanf_s("%c", &n);
n = getchar();
if (n != '$')
{
*s.top = n;//把值放进栈里边,双重指针表非指针,嘿嘿
s.top++;//头结点往上移动
}
else
return 1;
//scanf_s("%c", &n);
//if (n == '$')
// return 1;
//*s.top = n;//将n的值赋给top
//s.top++;//头结点往上移动
m++;
}
}
成功了哦,哈哈哈,再稍微修改一下下
修改之后发现
咋说呢
不止一条语句,要花括号括起来,检验的重要性
接下来进行入栈操作,入栈之前需要进行判满的操作
//进行入栈操作的编写,入栈之前需要进行判满的操作
Status PushStack(seqstack& s, ElemType& e)
{
if (s.top - s.base == 0)//判满
return 0;
else
*s.top++ = e;//把头结点向上移动后,把e的地址作为头结点的地址域
}
出栈文章来源:https://www.toymoban.com/news/detail-743130.html
//出栈,后进先出,则该元素为栈顶元素
char PopStack(seqstack& s)
{
if (StackEmpty == 0)
{
printf("--此栈为空栈--\n");
return 0;
}
else
{
char e;
s.top--;//因为头结点指向栈顶元素的上一个节点,所以需要下移指向栈顶元素
e = *s.top;// 实际上此元素并没真正删除,仍在s.top中,
//但是如果插入元素,就会被更新,就像是删除了一样
return e;
}
}
取栈顶元素和即为栈顶元素出栈文章来源地址https://www.toymoban.com/news/detail-743130.html
到了这里,关于顺序栈的基本操作(存储结构设计、初始化、判空、判满、入栈、出栈、取栈顶元素、遍历输出栈内元素)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!