zoukankan      html  css  js  c++  java
  • 桟的使用之算术表达式求值

    1.  背景知识

    对于算术表达式(1+((2+3)*(4+5))),如何使用程序进行计算能够很好表示运算符的优先级,从而获得正确的结果呢?简化处理,我们将算术表达式当做一个字符串,包含运算数,左括号,运算符和右括号,这里只处理带有加减乘除以及求平方根的运算。E.W.Dijkstra发明了一种简单的算法,使用两个栈,一个用于保存运算符,一个用于保存运算数,具体算法操作如下:

    表达式由括号,运算符和操作数组成,依据以下4中情况从左到右将这些实体送入桟中

    • 将操作数送入操作数桟;
    • 将运算符送入运算符桟;
    • 遇到左括号忽略;
    • 遇到右括号时,弹出一个运算符,弹出所需数量的操作数,并将运算符和操作数的结果送到操作数桟中;

    2.  模拟表达式计算过程

    使用两个桟来模拟表达式计算,如下图所示:

    3.  代码实现

    开发环境:eclipse+jdk(1.7.0_45)

    import java.util.Scanner;
    
    class Stack<Item> {
    	private Node first; // 栈顶元素
    	private int N; // 元素数量
    	private class Node {
    		Item item;
    		Node next;
    	}
    	
    	public boolean isEmpty() {
    		return first == null;
    	}
    	
    	public int size() {
    		return N;
    	}
    	
    	public void push(Item item) {
    		Node oldfirst = first;
    		first = new Node();
    		first.item = item;
    		first.next = oldfirst;
    		N++;
    	}
    	
    	public Item pop() {
    		Item item = first.item;
    		first = first.next;
    		N--;
    		return item;
    	}
    }
    
    public class Evaluate {
    	@SuppressWarnings("resource")
    	public static void main(String[] args) {
    		Stack<String> ops = new Stack<String>();
    		Stack<Double> vals = new Stack<Double>();
    		Scanner scanner = new Scanner(System.in);
    		
    		while(scanner.hasNext()) {
    			String s = scanner.next();
    			if (s.equals("("))
    			{
    				
    			} else if (s.equals("+")) {
    				ops.push(s);
    			} else if (s.equals("-")) {
    				ops.push(s);
    			} else if (s.equals("*")) {
    				ops.push(s);
    			} else if (s.equals("/")) {
    				ops.push(s);
    			} else if (s.equals("sqrt")) {
    				ops.push(s);
    			} else if (s.equals(")")) {
    				String op = ops.pop();
    				Double v = vals.pop();
    				if (op.equals("+")) {
    					v = vals.pop() + v;
    				} else if (op.equals("-")) {
    					v = vals.pop() - v;
    				} else if (op.equals("*")) {
    					v = vals.pop() * v;
    				} else if (op.equals("/")) {
    					v = vals.pop() / v;
    				} else if (op.equals("sqrt")) {
    					v = Math.sqrt(v);
    				}
    				vals.push(v);
    			} else {
    				vals.push(Double.parseDouble(s));
    			}
    		}
    		System.out.println(vals.pop());
    	}
    }
    

    这段代码为了简单起见要求输入表达式没有省略任何括号,数字和字符均以空白字符间隔:

    ------------------------------- 问道,修仙 -------------------------------
  • 相关阅读:
    Java实现 洛谷 P1064 金明的预算方案
    (Java实现) 洛谷 P1605 迷宫
    (Java实现) 洛谷 P1031 均分纸牌
    Java实现 洛谷 P1060 开心的金明
    三代名将却三代悲剧(绝对不要轻易招惹“关系户”,要学会适应规则)
    simulate windows postmessage or keydown
    qt 拖拽 修改大小(使用了nativeEvent和winEvent)
    QT下资源使用和资源占用…(可以动态加载资源文件,这样不占内存)
    qt实现头像上传功能(写了4个类,朝十晚八的博客,非常好)
    自定义ModelValidatorProvider
  • 原文地址:https://www.cnblogs.com/elvalad/p/4055582.html
Copyright © 2011-2022 走看看