顺序栈的基本实现及应用
- 数制转换
//数制转换(十进制转八进制)
int conversion(int num)
{
//对于输入的任意一个非负十进制整数,打印输出与其等值的八进制数
SqStack<int> s;
int e = 0;
int result = 0;
while(num)
{
s.Push(num % 8);
num /= 8;
}
while(s.IsEmpty() != EMPTY)
{
s.Pop(e);
result = result*10 + e;
}
return result;
}
将取模后的数逐个入栈,再逐个出栈。
- 表达式求值
中缀表达式求值
创建两个栈,一个保存符号,一个保存数据。
//判断优先级
char Precede(char o1, char o2)
{
char f=' ';
switch(o2)
{
case '+':
case '-':
if(o1 == '(' || o1 == '#') //栈中符号优先级低
{
f = '<';
}
else
{
f = '>';
}
break;
case '*':
case '/':
if(o1=='*' || o1=='/' || o1==')')
{
f = '>';
}
else
{
f = '<';
}
break;
case '(':
if(o1 == ')')
{
cout<< "括号匹配错误!"<<endl;
exit(ERROR);
}
else
{
f = '<';
}
break;
case ')':
switch(o1)
{
case '(':
f = '='; //括号匹配
break;
case '#':
cout<< "输入了错误的括号!~"<<endl;
exit(ERROR);
default:
f = '>'; //其他情况站定元素的优先级更大
}
break;
case '#':
switch(o1)
{
case '#':
f = '=';
break;
case '(':
cout<< "表达式中有多余的括号!!"<<endl;
exit(ERROR);
default:
f = '>';
}
}
return f;
}
//运算函数
int Operate(int a, char theta, int b)
{
switch(theta)
{
case '+':
return a+b;
break;
case '-':
return a-b;
break;
case '*':
return a*b;
break;
case '/':
return a/b;
break;
}
return 0;
}
int EvalExpr(char *ptr)
{
SqStack<char> OPTR; //操作符栈
OPTR.Push('#'); //表达式起始符为'#'
SqStack<int> OPND; //操作数栈
char op, c, theta=' ', x, m;
int a=0, b=0;
c = *ptr++; //每一个数当做字符取出,ptr遍历后移
OPTR.GetTop(op);
while(c != '#' || op != '#')
{
if(!In(c)) //如果是数字直接进栈
{
m = atoi(&c); //将字符转化为数字
OPND.Push(m); //数字入栈
c = *ptr++; //指针后移
}
else //如果是符号的话,则先将这个符号与栈顶符号进行比较
{
switch(Precede(op, c))
{
case '<': //栈中符号优先级低,继续进栈
OPTR.Push(c);
c = *ptr++;
break;
case '=': //优先级相等时,说明遇到括号,需要托括号
OPTR.Pop(x); //脱括号
c = *ptr++;
break;
case '>': //栈中符号优先级高时,先计算,再将结果压入栈中
OPTR.Pop(theta); //运算符
OPND.Pop(b); //操作数
OPND.Pop(a);
OPND.Push(Operate(a, theta, b)); //将新的运算结果插到栈中
break;
}
}
OPTR.GetTop(</