栈的应用——表达式求值

中缀表达式:常见的算术表达式,操作符号在两个操作数之间,例:1+1

后缀表达式:也叫逆波兰式,操作符号在两个操作数后,不含有括号,例:1 1 +

1、后缀表达式求值

算法:遇到操作数将操作数入栈,遇到操作符号则取出栈顶的两个元素进行运算,并将运算结果入栈

输入格式:每个操作数、操作符号用空格隔开

例:6 2 / 3 - 4 2 * +

package com.company;

import java.util.Scanner;
import java.util.Stack;

public class Main {
    public static void main(String[] args) {
        Scanner input = new Scanner(System.in);
        String expression = input.nextLine();
        Stack<Integer> stack = new Stack<Integer>();
        for(int i=0;i<expression.length();i++){
            char now = expression.charAt(i);
            if(now=='+'||now=='-'||now=='*'||now=='/') {
                int b = stack.pop().intValue();
                int a = stack.pop().intValue();
                switch (now) {
                    case '+':a=a+b;break;
                    case '-':a=a-b;break;
                    case '*':a=a*b;break;
                    case '/':a=a/b;break;
                }
                stack.push(Integer.valueOf(a));
                i++;//skip space
                continue;
            }
            String temp="";
            while(now != ' '){
                temp+=now;
                i++;
                now=expression.charAt(i);
            }
            stack.push(Integer.valueOf(temp));
        }
        int ans = stack.pop().intValue();
        System.out.println(ans);
    }
}

2、中缀表达式转后缀表达式

(1)将操作数直接输出

(2)遇到 '(' 则入栈,遇到 ')' 则从栈顶依次输出操作符,直到遇到 '('

(3)每当遇到一个操作符号,与当前栈顶的操作符号进行优先级比较。若当前操作符号优先级更高,则入栈,否则弹出栈顶的操作符号,将当前操作符号入栈

package com.company;

import java.util.HashMap;
import java.util.Map;
import java.util.Scanner;
import java.util.Stack;

public class Main {
    public static void main(String[] args) {
        Scanner input = new Scanner(System.in);
        String expression = input.nextLine();
        String ans="";
        Stack<Character> stack = new Stack<Character>();
        Map<Character,Integer> map = new HashMap<Character, Integer>();
        map.put('(',0);
        map.put('+',1);
        map.put('-',1);
        map.put('*',2);
        map.put('/',2);
        boolean flag = false;
        for(int i=0;i<expression.length();i++){
            char now = expression.charAt(i);
            if(now=='(') {
                stack.push(Character.valueOf(now));
            }
            else if(now=='+'||now=='-'||now=='*'||now=='/') {
                if(stack.empty()){
                    stack.push(Character.valueOf(now));
                }else {
                    char top = stack.peek().charValue();
                    if (map.get(now).intValue()<=map.get(top).intValue()){
                        ans+=stack.pop().charValue();
                        ans+=' ';
                        stack.push(Character.valueOf(now));
                    }else
                        stack.push(Character.valueOf(now));
                }
            } else if(now==')'){
                char top;
                while(true){
                    top = stack.pop().charValue();
                    if(top=='(')
                        break;
                    ans+=top;
                    ans+=' ';
                }
            }else{
                while(now>='0'&&now<='9') {
                    ans += now;
                    i++;
                    if(i<expression.length())
                        now = expression.charAt(i);
                    else
                        break;
                }
                ans+=' ';
                i--;
            }
        }
        while(!stack.empty()){
            ans+=' ';
            ans+=stack.pop().charValue();
        }
        System.out.println(ans);
    }
}

3、中缀表达式求值

基本思想:结合中缀表达式转后缀表达式和后缀表达式求值的思想,设置两个栈,一个栈保存操作符号,一个栈保存操作数;每当弹出一个操作符,就弹出栈顶的两个操作数,并将计算结果入栈

package com.company;

import java.util.HashMap;
import java.util.Map;
import java.util.Scanner;
import java.util.Stack;
public class Main {
    public static Stack<Character> symbol;
    public static Stack<Integer> operand;
    public static void calculate(char c){
        int b = operand.pop().intValue();
        int a = operand.pop().intValue();
        switch (c){
            case '+':a=a+b;break;
            case '-':a=a-b;break;
            case '*':a=a*b;break;
            case '/':a=a/b;break;
        }
        operand.push(Integer.valueOf(a));
    }
    public static void main(String[] args) {
        Scanner input = new Scanner(System.in);
        String expression = input.nextLine();
        symbol = new Stack<Character>();
        operand = new Stack<Integer>();
        Map<Character,Integer> map = new HashMap<Character, Integer>();
        map.put('(',0);
        map.put('+',1);
        map.put('-',1);
        map.put('*',2);
        map.put('/',2);
        boolean flag = false;
        for(int i=0;i<expression.length();i++){
            char now = expression.charAt(i);
            if(now=='(') {
                symbol.push(Character.valueOf(now));
            }
            else if(now=='+'||now=='-'||now=='*'||now=='/') {
                if(symbol.empty()){
                    symbol.push(Character.valueOf(now));
                }else {
                    char top = symbol.peek().charValue();
                    if (map.get(now).intValue()<=map.get(top).intValue()){
                        char c = symbol.pop().charValue();
                        calculate(c);
                        symbol.push(Character.valueOf(now));
                    }else
                        symbol.push(Character.valueOf(now));
                }
            } else if(now==')'){
                char top;
                while(true){
                    top = symbol.pop().charValue();
                    if(top=='(')
                        break;
                    calculate(top);
                }
            }else{
                String temp="";
                while(now>='0'&&now<='9') {
                    temp += now;
                    i++;
                    if(i<expression.length())
                        now = expression.charAt(i);
                    else
                        break;
                }
                operand.push(Integer.valueOf(temp));
                i--;
            }
        }
        while(!symbol.empty()){
            char c = symbol.pop().charValue();
            calculate(c);
        }
        int ans = operand.pop().intValue();
        System.out.println(ans);
    }
}

 

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值