首页 > 其他分享 >2022-11-10 Acwing每日一题

2022-11-10 Acwing每日一题

时间:2022-11-11 14:14:56浏览次数:77  
标签:11 10 符号 int num 取整 2022 表达式 op

本系列所有题目均为Acwing课的内容,发表博客既是为了学习总结,加深自己的印象,同时也是为了以后回过头来看时,不会感叹虚度光阴罢了,因此如果出现错误,欢迎大家能够指出错误,我会认真改正的。同时也希望文章能够让你有所收获,与君共勉!

表达式求值

给定一个表达式,其中运算符仅包含+,-,*,/(加 减 乘 整除),可能包含括号,请你求出表达式的最终值。

注意:

数据保证给定的表达式合法。
题目保证符号 - 只作为减号出现,不会作为负号出现,例如,-1+2,(2+2)*(-(1+1)+2) 之类表达式均不会出现。
题目保证表达式中所有数字均为正整数。
题目保证表达式在中间计算过程以及结果中,均不超过 231−1。
题目中的整除是指向 0 取整,也就是说对于大于 0 的结果向下取整,例如 5/3=1,对于小于 0 的结果向上取整,例如 5/(1−4)=−1
C++和Java中的整除默认是向零取整;Python中的整除//默认向下取整,因此Python的eval()函数中的整除也是向下取整,在本题中不能直接使用。
输入格式
共一行,为给定表达式。

输出格式
共一行,为表达式的结果。

数据范围
表达式的长度不超过 105。

输入样例:
(2+2)*(1+1)
输出样例:
8

算法原理

①从表达式中分离出一个个数字整体(所以while循环对于“123”这样的整个数作为整体处理。)
②遇到符号,要按照符号的优先级运算。
这里的op是优先级单调递增栈。

  • 如果当前运算优先级比栈顶高,就直接压栈。
  • 如果当前的与之前相等或更低,且符号栈的顶部符号不是左括号(,且符号栈存在符号,则先进行取栈顶符号运算,再将当前符号加入到符号栈中-。如:2+3*4+5,符号栈先进+,*号比+的优先级要大,所以直接进栈,后面的加号比*的优先级要小,所以要先进行乘法运算

③括号是特殊处理的,如果没有遇到右括号,则运算最多只能处理到上一个左括号,例如2*(3+4),在加号位置不能先算2*3,而是先等待,因为符号栈顶部是(,再括号里面如果存在像2*(2+3*4+5),按照规则2也会先把3*4算出来并放进数字栈中,直到遇到)就从右到左取出数字栈中的数字(符号栈顶的符号)进行运算直至左括号(。

代码实现

#include <iostream>
#include <string>
#include <algorithm>
#include <stack>
#include<unordered_map>

using namespace std;

stack<int> num;
stack<char> op;


void eval(){
    int b = num.top(); num.pop();
    int a = num.top(); num.pop();
    char c =op.top() ;op.pop();
    int x ;
    if(c == '+')   x = a+b;
    else if(c == '-')  x= a-b;
    else if(c == '*')  x= a*b;
    else x = a/b;
    num.push(x);
}


int main(void){
    unordered_map<char,int> pr{{'+',1},{'-',1},{'*',2},{'/',2}};    // 定义恏优先级
    string str;
    
    cin >> str;
    
    for(int i=0; i < str.size() ; i++){
        auto c = str[i];
        if(isdigit(c)){
            int x = 0, j=i;
            while(j<str.size() && isdigit(str[j])){ // 将字符串转化成数字
                x = x * 10 + str[j++] - '0';
                // j++;
            }
            i = j-1;
            num.push(x);
        }
        else if (c == '('){    // 左括号直接进符号栈
            op.push(c);
        }
        else if (c == ')'){    // 右括号:从右到左进行运算,知道遇到左括号停下,并且弹出左括号
            while(op.top() != '(')  eval();
            op.pop();
        }
        else{   // 遇到普通操作符
            // 符号栈不为空,栈顶符号不为"(",当前符号的优先级比栈顶的要小(-,+),说明栈顶符号为*/,
            while(op.size() && op.top() != '(' && pr[op.top()] >= pr[c])   eval();
            op.push(c);    // 要先进行乘除运算后再将+,-存入符号栈中。
        }
    }
    
    while(op.size()) eval();    // 最后对+,-运算进行操作
    cout << num.top() << endl;  // 最后的num一定是运算结果。
    return 0;    
}



标签:11,10,符号,int,num,取整,2022,表达式,op
From: https://www.cnblogs.com/WangChe/p/16879131.html

相关文章

  • 2022.11.11 函数式接口
    5.函数式接口5.1概述只有一个抽象方法的接口我们称之为函数接口。JDK的函数式接口都加上了@FunctionalInterface(与重写方法的注解作用类似,校验作用)注解进行标识。......
  • 2022.11.11 方法引用与lambda并行流
    6.方法引用我们在使用lambda时,如果方法体中只有一个方法的调用的话(包括构造方法),我们可以用方法引用进一步简化代码。6.1推荐用法我们在使用lambda时不需要考虑什么时......
  • 2022.11.11 Lambda表达式
    2.Lambda表达式2.1概述Lambda是JDK8中一个语法糖。他可以对某些匿名内部类的写法进行简化。它是函数式编程思想的一个重要体现。让我们不用关注是什么对象。而是更关......
  • 2022.11.11 Stream流
    3.Stream流3.1概述Java8的Stream使用的是函数式编程模式,如同它的名字一样,它可以被用来对集合或数组进行链状流式的操作。可以更方便的让我们对集合或数组操作。 3.......
  • 2022.11.11 Optional
    4.Optional4.1概述我们在编写代码的时候出现最多的就是空指针异常。所以在很多情况下我们需要做各种非空的判断。例如: Authorauthor=getAuthor(); if(author!=n......
  • loj#10064 黑暗城堡
     求图中的最短路径生成树有多少个?(该生成树中的任意点i,i到1的距离和 原图中的i到1的最短距离相等  跑所有点到1的单源最短路,d[i] ifd[i]==d[y]+z,那么z这个路......
  • 1024竟是官方节日,祝大家节日快乐
    不知不觉,又到了一年一度的1024程序员节,在今天的这个特殊的日子里,祝广大“程序猿”朋友:1024,不再996,bug退散,发量惊人。尤其是在2020年,这个节日好像被赋予了更深层次的味道~来......
  • 1. 演进、环境与资源-20221111
    C++11也叫2.0了解:之前std:tr1的内容都已经放到std内了搜索:   :Gcc:unix家族,MinGW:windows家族   选择支持C++11还是14:【右击项目】–【选择属性】–【C/C++......
  • [JavaScript-10]this指向
    1.默认绑定//全局环境指向windowconsole.log(this);//函数独立调用,函数内部this指向windowfunctionfn(){console.log(this);}fn();//函数当做对象方法......
  • Ubuntu 21.10 (Impish Indri) Reached End of Life, Upgrade to Ubuntu 22.04 LTS Now
    https://9to5linux.com/ubuntu-21-10-impish-indri-reached-end-of-life-upgrade-to-ubuntu-22-04-lts-now......