C语言oj四则运算调用函数,小米OJ-16-四则运算

描述

实现一个算法,可以进行任意非负整数的加减乘除组合四则运算。

请注意运算符的优先级。

输入

请输入一行算式,使用空格分隔数字与运算符。

数字为任意非负整数,运算符为+ - * /,不考虑括号。

输出

输出算式的运算结果。如果是小数,请向下取整(包含中间步骤结果)。 如果出现“除0异常”,输出err。

输入样例

3 + 5

12 + 45 / 9

1 / 2

1 / 0

12 + 34 * 56 - 78

输出样例

8

17

0

err

1838

解析:这一题是关于非负整数的四则运算,不包括"("和")"。整体思路是把输入的中缀表达式转化为后缀表达式,然后通过后缀表达式求值。

中缀表达式TO后缀表达式

(这个思路是包含括号运算符的)

利用两个队列in,suf和一个栈ope:其中in存放中缀表达式,suf存放后缀表达式,ope存放运算符

从左往右遍历中缀表达式,如果遇到数字,则放入suf中,如果遇到操作符,则放入ope中。在放操作符的时候有一定的规则,如果栈为空或栈顶元素为(,则直接压栈。如果是(,也直接压栈;如果栈顶元素为普通操作符,则比较优先级,如果待压栈的操作符比栈顶操作符优先级高,则直接压栈,否则将ope中的栈顶元素出栈,并压入suf中,再接着比较ope栈顶元素的优先级。如果遇到),则依次弹出ope栈顶的运算符,并压入suf,直到遇到左括号为止,此时将这一对括号丢弃。最后将ope中剩余的运算符依次弹出并压入suf,便得到了后缀表达式。(注意:等号的优先级最低,因为要到最后才进行赋值操作)

4a66262d9639?amp%3Butm_medium=seo_notes&amp%3Butm_source=recommendation

大致过程.png

代码如下,这一题写的代码比较笨,如果运算符种类比较多的话应该为每个运算符设置优先级。

//中缀转化为后缀

void intosuf (queue &in , queue &suf)

{

//存放运算符

stack ope;

for(; !in.empty() ; in.pop())

{

auto c = in.front();

if(c != "+" && c != "-" && c != "*" && c != "/")

{

suf.push(c);

}

else if((c == "+" || c == "-" ) && !ope.empty())

{

while((c == "+" || c == "-" ) && !ope.empty())

{

suf.push(ope.top());

ope.pop();

}

ope.push(c);

}

else if(ope.empty())

{

ope.push(c);

}

else if((c == "*" || c == "/" ) && !ope.empty() && (ope.top() == "+" || ope.top() == "-" ))

{

ope.push(c);

}

else if((c == "*" || c == "/" ) && !ope.empty() && (ope.top() == "*" || ope.top() == "/" ))

{

while((c == "*" || c == "/" ) && !ope.empty() && (ope.top() == "*" || ope.top() == "/" ))

{

suf.push(ope.top());

ope.pop();

}

ope.push(c);

}

}

while(!ope.empty())

{

suf.push(ope.top());

ope.pop();

}

}

利用后缀表达式求值

后缀表达式的求值规则为:从左到右扫描后缀表达式,如果遇到操作数,将其压入栈中,如果遇到操作符,则从栈中弹出两个操作数,计算结果,然后把结果入栈,直到遍历完后缀表达式,则计算完成,此时的栈顶元素即为计算结果。

没有写额外的函数来封装,直接写在main里面了

int main()

{

string input;

while(getline(cin,input))

{

//分别放中缀后缀表达式

queue infix;

queue suffix;

//运算用到的栈

stack calculation;

//出错标志

int err = 0;

stringstream ss(input);

string item;

while(getline(ss,item,' '))

{

infix.push(item);

}

intosuf(infix,suffix);

for(; !suffix.empty() ; suffix.pop())

{

auto c = suffix.front();

if(c != "+" && c != "-" && c != "*" && c != "/")

{

calculation.push(c);

}

else if(c == "+")

{

int i = stoi(calculation.top());

calculation.pop();

int j = stoi(calculation.top());

calculation.pop();

calculation.push(to_string(i+j));

}

else if(c == "-")

{

int i = stoi(calculation.top());

calculation.pop();

int j = stoi(calculation.top());

calculation.pop();

calculation.push(to_string(j-i));

}

else if(c == "*")

{

int i = stoi(calculation.top());

calculation.pop();

int j = stoi(calculation.top());

calculation.pop();

calculation.push(to_string(i*j));

}

else if(c == "/")

{

int i = stoi(calculation.top());

calculation.pop();

int j = stoi(calculation.top());

calculation.pop();

if(i == 0)

{

err = 1;

break;

}

calculation.push(to_string(j/i));

}

}

if(err == 0)

{

cout<

}

else

{

cout<

}

}

return 0;

}

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值