中缀转后缀并计算

如有问题,请各位大虾指正

public class Analyze
    {

        private Stack<string> stack;//存运算符
        private ArrayList post;//存后缀表达式
        private Stack<float> result;//存计算结果

        public Analyze()
        {
            stack = new Stack<string>();
            post = new ArrayList();
            result = new Stack<float>();
        }

        public float Calculate(string expression)
        {
            ArrayList items = getItem(expression);
            Merger(items);
            return Sum();
        }

        #region 获得分解后的list
        private ArrayList getItem(string expression)
        {
            string lastNum = string.Empty;
            ArrayList items = new ArrayList();
            for (int i = 0; i < expression.Length; i++)
            {
                if (char.IsNumber(expression[i]) || expression[i].Equals('.'))
                {
                    lastNum += expression[i];
                }
                else
                {
                    if (lastNum != string.Empty)
                    {
                        items.Add(lastNum);
                        lastNum = string.Empty;
                    }
                    items.Add(expression[i]);
                }
            }
            if (lastNum != string.Empty)
            {
                items.Add(lastNum);
                lastNum = string.Empty;
            }
            return items;
        }
        #endregion

        #region 转换成后缀表达式
        /**
         * 从左到右扫描中缀表达式:
         * (1)若读到的是操作数,直接存入post栈
         * (2)若读到的是(,则直接存入stack栈
         * (3)若读到的是),则将stack栈中(前的所有运算符出栈,存入post栈
         * (4)若读到的是其它运算符,则将该运算符和stack栈顶运算符作比较:若高于或等于栈顶运算符,
         * 则直接存入stack栈,否则将栈顶运算符(所有优先级高于读到的运算符的,不包括括号)出栈,存入post栈。
         * 最后将读到的运算符入栈。
         * 当扫描完后,stack栈中还在运算符时,则将所有的运算符出栈,存入post栈
         */
        private void Merger(ArrayList items)
        {
            foreach (var o in items)
            {
                string item = o.ToString();
                if (Regex.IsMatch(item, @"^(([1-9][0-9]*.[0-9][0-9]*)|([0].[0-9][0-9]*)|([1-9][0-9]*)|([0]{1}))$"))
                {
                    post.Add(item);
                    continue;
                }
                if (item.Equals("("))
                {
                    stack.Push(item);
                    continue;
                }
                if (item.Equals(")"))
                {
                    while (!stack.Peek().Equals("("))
                    {
                        post.Add(stack.Pop());
                    }
                    stack.Pop();
                    continue;
                }
                if (item.Equals("+") || item.Equals("-") || item.Equals("*") || item.Equals("/"))
                {
                    if (stack.Count == 0)
                    {
                        stack.Push(item);
                        continue;
                    }
                    string tempStack = stack.Peek();
                    if (((item.Equals("*") || item.Equals("/")) &&
                    (tempStack.Equals("+") || tempStack.Equals("-")))||tempStack.Equals("("))
                    {
                        stack.Push(item);
                    }
                    else
                    {
                        post.Add(stack.Pop());
                        stack.Push(item);
                    }
                    continue;
                }
            }
            while (stack.Count>0)
            {
                post.Add(stack.Pop());
            }
        }
        #endregion

        #region 后缀表达式计算值
        /**
         * 从左到右遍历表达式的每个数字和符号,遇到是数字就进栈,
         * 遇到是符号,就将处于栈顶两个数字出栈,
         * 进行运算,运算结果进栈,一直到最终获得结果。
         */
        private float Sum()
        {
            float re = 0;
            foreach(string item in post){
                if (Regex.IsMatch(item, @"^(([1-9][0-9]*.[0-9][0-9]*)|([0].[0-9][0-9]*)|([1-9][0-9]*)|([0]{1}))$"))
                {
                    result.Push(float.Parse(item));
                    continue;
                }
                if (item.Equals("+") || item.Equals("-") || item.Equals("*") || item.Equals("/"))
                {
                    float num1 = result.Pop();
                    float num2 = result.Pop();
                    switch (item)
                    {
                        case "+":
                            re = num2 + num1;
                            break;
                        case "-":
                            re = num2 - num1;
                            break;
                        case "*":
                            re = num2 * num1;
                            break;
                        case "/":
                            re = num2 / num1;
                            break;
                    }
                    result.Push(re);
                    continue;
                }
            }
            return result.Pop();
        }
        #endregion
    }
View Code

程序展现:

原文地址:https://www.cnblogs.com/margin-gu/p/5260901.html