手工栈的简单实现是借用数组完成,可以实现入栈出栈,检查栈是否为空等操作,实现的栈具有先进后出的特性。
typedef struct Stack
{
char data[1001]; //用来存放记录在栈中的数据
int top; //栈顶指针
int base; //栈底指针
}Stack;
Stack s;
其中栈顶栈底指针记录的是数组的下标,栈顶指针指向数组顶元素的下一个位置。
void s_init(Stack *s) //栈初始化
{
s->top=0;
s->base=0;
}
void s_push(Stack *s, char c) //元素c入栈
{
s->data[s->top++]=c;
}
void s_pop(Stack *s, char *e) //弹出栈顶元素,栈顶元素出栈,并且通过指针e来返回该元素的值
{
(*e)=s->data[--s->top]
}
int s_num(Stack *s) //返回栈的大小
{
return s->top-s->base;
}
bool s_empty(Stack *s) //检查栈是否为空
{
if(s->top==0)
return true;
else
return false;
}
问题 1681: 算法3-2:行编辑程序
时间限制: 1Sec 内存限制: 32MB 提交: 27 解决: 14
题目描述
一个简单的行编辑程序的功能是:接收用户从终端输入的程序或数据,并存入用户的数据区。由于用户在终端上进行输入时,不能保证不出差错,因此,若在编辑程序中,“每接收一个字符即存入用户数据区”的做法显然不是很恰当。较好的做法是,设立一个输入缓冲区,用以接收用户输入的一行字符,然后逐行存入用户数据区。允许用户输入出差错,并在发现有误时可以及时更正。例如,当用户发现刚刚键入的一个字符是错的时,可补进一个退格符“#”,以表示前一个字符无效;如果发现当前键入的行内错误较多或难以补救,则可以键入一个退行符“@”,以表示当前行中的字符均无效。例如假设从终端接收了这样的两行字符:
whil##ilr#e(s#*s)
outcha@ putchar(*s=#++);
则实际有效的是下列两行:
while(*s)
putchar(*s++);
输入
若干行程序或者数据,每行不超过200个字符。
输出
经过行编辑程序处理过后的输出。
样例输入
whil##ilr#e(s#*s) outcha@ putchar(*s=#++);
样例输出
while(*s) putchar(*s++);
思路可以使用栈来储存每一行的数据,如果遇到#字符则弹出栈顶元素,遇到@字符则清空栈(令栈初始化),其余字符则入栈
#include<iostream>
using namespace std;
typedef struct Stack
{
char data[201];
int top, base;
}Stack;
Stack s;
void s_init(Stack *s)
{
s->top = 0;
s->base = 0;
}
void s_push(Stack *s, char c)
{
s->data[s->top++] = c;
}
void s_pop(Stack *s, char *e)
{
*e = s->data[--s->top];
}
bool s_empty(Stack *s)
{
if (s->top == 0)
return true;
else
return false;
}
int main()
{
char c, input[201];
while (cin.getline(input,201,'\n')) //注意此处不断输入一行可能会有空格不能使用cin或scanf
{
s_init(&s);
for (int i = 0; input[i] != '\0'; i++)
{
if (input[i] == '#')
s_pop(&s, &c);
else if (input[i] == '@')
s_init(&s);
else
s_push(&s, input[i]);
}
while (s.base != s.top) //自底向顶的输出栈元素的值
{
cout << s.data[s.base++];
}
cout << endl;
}
return 0;
}