zoukankan      html  css  js  c++  java
  • 逆波兰表达式3(后缀表达式求值)

    逆波兰表达式(后缀表达式求值)
    
    ##1 描述
    
    计算后缀表达式 [9,3,1,-,3,*,+,10,2,/,+ ]
    
    现在我们已经将表达式专为后缀表达式了,马上需要对这个表达式进行求值。
    
    计算规则:
    
    从左到右遍历每个数字,以及符号。
    
    1)如果为数字,则进栈 
    
    2)如果为符号,则栈顶的2个数字出栈并进行计算。然后将结果入栈
    
    一直到获取到最终结果。
    
    	package main
    	
    	import (
    		"fmt"
    		"strconv"
    	)
    	
    	/*
    	 *	定义节点
    	 */
    	type Node struct {
    		data string
    		next *Node
    	}
    	
    	/*
    	 *	定义栈
    	 */
    	type Stack struct {
    		top    *Node
    		length int
    	}
    	
    	func NewStack() *Stack {
    		return &Stack{top: nil, length: 0}
    	}
    	
    	/*
    	 * 压栈
    	 */
    	func (list *Stack) Push(data string) error {
    	
    		node := &Node{data: data, next: list.top}
    		list.top = node
    		list.length++
    		return nil
    	}
    	
    	/*
    	 *	出栈
    	 */
    	func (list *Stack) Pop() (string, error) {
    	
    		if list.length == 0 {
    			return "", fmt.Errorf("the list is empty")
    		}
    	
    		node := list.top
    		list.top = node.next
    		list.length--
    		return node.data, nil
    	}
    	
    	/**************************************************/
    	//栈外优先级icp(In coming priority)
    	func GetIcp(oper string) int {
    		switch oper {
    		case ")":
    			return 1
    		case "(":
    			return 8
    		case "+":
    			fallthrough
    		case "-":
    			return 2
    		case "*":
    			fallthrough
    		case "/":
    			fallthrough
    		case "%":
    			return 4
    		case "#":
    			return 0
    		}
    		return 0
    	}
    	
    	//栈内优先级isp(In stack priority)
    	func GetIsp(oper string) int {
    		switch oper {
    		case ")":
    			return 8
    		case "(":
    			return 1
    		case "+":
    			fallthrough
    		case "-":
    			return 3
    		case "*":
    			fallthrough
    		case "/":
    			fallthrough
    		case "%":
    			return 5
    		case "#":
    			return 0
    		}
    		return 0
    	}
    	
    	func IsOperator(oper string) bool {
    		switch oper {
    		case "(":
    			fallthrough
    		case ")":
    			fallthrough
    		case "+":
    			fallthrough
    		case "-":
    			fallthrough
    		case "*":
    			fallthrough
    		case "/":
    			return true
    		default:
    			return false
    		}
    		return false
    	}
    	
    	func DoOperator(oper string, number1 int, number2 int) int {
    		switch oper {
    	
    		case "+":
    			return number1 + number2
    		case "-":
    			return number1 - number2
    		case "*":
    			return number1 * number2
    		case "/":
    			return number1 / number2
    		default:
    			return 0
    		}
    		return 0
    	}
    	
    	func CenterToEnd(expr []string) []string {
    		stack := &Stack{top: &Node{data: "#", next: nil}, length: 0}
    		retexpr := make([]string, 0)
    		for _, v := range expr {
    			if !IsOperator(v) {
    				retexpr = append(retexpr, v)
    	
    			} else {
    				if stack.length == 0 {
    	
    					stack.Push(v)
    				} else {
    					//遇到")",则出栈并输出。直到"(","("出栈不输出。
    					if GetIcp(v) == 1 {
    	
    						for GetIcp(stack.top.data) != 8 {
    							data, _ := stack.Pop()
    							retexpr = append(retexpr, data)
    						}
    						stack.Pop()
    	
    					} else if GetIcp(v) >= GetIsp(stack.top.data) {
    						//比较运算符>的情况
    						stack.Push(v)
    	
    					} else {
    						//比较运算符<=的情况
    						for GetIcp(v) < GetIsp(stack.top.data) {
    							data, _ := stack.Pop()
    							retexpr = append(retexpr, data)
    						}
    						stack.Push(v)
    	
    					}
    	
    				}
    	
    			}
    	
    		}
    	
    		//输出栈中剩余计算符
    		for stack.length > 0 {
    			data, _ := stack.Pop()
    			retexpr = append(retexpr, data)
    		}
    		fmt.Println("后缀表达式:", retexpr)
    		return retexpr
    	
    	}
    	
    	func calculate(expr []string) string {
    		stack := &Stack{top: &Node{data: "#", next: nil}, length: 0}
    		//retexpr := make([]string, 0)
    		for _, v := range expr {
    			if !IsOperator(v) {
    				stack.Push(v)
    			} else {
    				str1, _ := stack.Pop()
    				str2, _ := stack.Pop()
    				number1, _ := strconv.ParseInt(str1, 10, 32)
    				number2, _ := strconv.ParseInt(str2, 10, 32)
    	
    				number3 := DoOperator(v, int(number2), int(number1))
    				ret := strconv.FormatInt(int64(number3), 10)
    				stack.Push(ret)
    	
    			}
    		}
    	
    		result, _ := stack.Pop()
    		return result
    	}
    	func main() {
    		expr := []string{"9", "+", "(", "3", "-", "1", ")", "*", "3", "+", "10", "/", "2"}
    		retexpr := CenterToEnd(expr)
    		fmt.Println("计算结果", calculate(retexpr))
    	
    	}
    
  • 相关阅读:
    用jQuery写的一个简单的弹出窗口(IE7\IE8\FF3)
    live write test
    sql2
    查询所有表索引
    java初学问题记录(2012.02.092012.02.16)
    SQL
    centso7网卡bond
    vmware模板
    Dockerfile参考
    Docker简单介绍
  • 原文地址:https://www.cnblogs.com/sxt102400/p/3039697.html
Copyright © 2011-2022 走看看