首页 > Windows开发 > 详细

c# 解释器模式与sping.net表达式的结合应用(金融里经常需要用到公式,这个公式是抽象的需要自己解释)

时间:2017-01-08 16:24:14      阅读:371      评论:0      收藏:0      [点我收藏+]
.上代码
using Spring.Expressions;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleApplication48
{
    public abstract class Expression
    {

        //解析公式和数值,其中var中的key值是是公式中的参数,value值是具体的数字
        //这里字典可以抽象为上下文 ctx,此处自己扩展
        public abstract string interpreter(Dictionary<string, int> var);

    }

    public class VarExpression : Expression
    {


        private string key;

        public VarExpression(string _key)
        {

            this.key = _key;

        }

        //从map中取之

        public override string interpreter(Dictionary<string, int> var)
        {

            return var[key].ToString();

        }

    }


    public abstract class SymbolExpression : Expression
    {

        protected Expression left;

        protected Expression right;

        //所有的解析公式都应只关心自己左右两个表达式的结果

        public SymbolExpression(Expression _left, Expression _right)
        {

            this.left = _left;

            this.right = _right;

        }
        

    }

    public class AddExpression : SymbolExpression
    {


        public AddExpression(Expression _left, Expression _right) : base(_left, _right)
        {


        }

        //把左右两个表达式运算的结果加起来

        public override string interpreter(Dictionary<string, int> var)
        {

            return (base.left.interpreter(var)) +"+"+( base.right.interpreter(var));

        }

    }
    public class SubExpression : SymbolExpression
    {


        public SubExpression(Expression _left, Expression _right) : base(_left, _right)
        {



        }

        //左右两个表达式相减

        public override string interpreter(Dictionary<string, int> var)
        {

            return base.left.interpreter(var) +"-"+ base.right.interpreter(var);

        }

    }
    public class PExpression : SymbolExpression
    {


        public PExpression(Expression _left, Expression _right) : base(_left, _right)
        {



        }

        //左右两个表达式相减

        public override string interpreter(Dictionary<string, int> var)
        {

            return base.left.interpreter(var)+"^"+base.right.interpreter(var);

        }

    }



    public class Calculator
    {

        //定义的表达式

        private Expression expression;

        //构造函数传参,并解析

        public Calculator(string expStr)
        {

            //定义一个堆栈,安排运算的先后顺序

            Stack<Expression> stack = new Stack<Expression>();

            //表达式拆分为字符数组

            char[] charArray = expStr.ToCharArray();

            //运算

            Expression left = null;

            Expression right = null;

            for (int i = 0; i < charArray.Length; i++)
            {

                switch (charArray[i])
                {

                    case +: //加法

                        //加法结果放到堆栈中

                        left = stack.Peek();

                        right = new VarExpression(charArray[++i].ToString());

                        stack.Push(new AddExpression(left, right));

                        break;

                    case -:

                        left = stack.Peek();

                        right = new VarExpression(charArray[++i].ToString());

                        stack.Push(new SubExpression(left, right));

                        break;
                    case ^:

                         left = stack.Peek();

                        right = new VarExpression(charArray[++i].ToString());

                        stack.Push(new PExpression(left, right));
                        break;
                    default: //公式中的变量

                        stack.Push(new VarExpression(charArray[i].ToString()));
                        break;


                }

            }

            //把运算结果抛出来

            this.expression = stack.Peek();

        }

        //开始运算

        public string run(Dictionary<string, int> var)
        {

            return this.expression.interpreter(var);

        }

    }


    public class Client
    {

        //运行四则运算

        public static void Main(string[] args)
        {

            Spring.Expressions.Expression e = new Spring.Expressions.Expression();
            string exp = "3^2+4^2";
           
            string expStr = getExpStr();

            //赋值 得到终结符

            Dictionary<string, int> var = getValue(expStr);

            Calculator cal = new Calculator(expStr);
            exp = cal.run(var);
            var val = ExpressionEvaluator.GetValue(null, exp);
            Console.WriteLine("运算结果为:" + expStr + "=" +exp+"="+val.ToString());
            Console.ReadKey();

        }

        //获得表达式

        public static String getExpStr()
        {

            Console.WriteLine("请输入表达式:");

            return Console.ReadLine();

        }

        //获得值映射

        public static Dictionary<string, int> getValue(string exprStr)
        {

            Dictionary<string, int> map = new Dictionary<string, int>();

            //解析有几个参数要传递

            foreach (char ch in exprStr.ToCharArray())
            {

                if (ch != + && ch != -&&ch!=^)
                {

                    //解决重复参数的问题

                    if (!map.ContainsKey(ch.ToString()))
                    {
                        Console.WriteLine("请输入" + ch + "的值:");

                        string in1 = Console.ReadLine();

                        map.Add(ch.ToString(), int.Parse(in1));

                    }

                }

            }

            return map;

        }

    }


}
2.例子
技术分享技术分享

 


 

c# 解释器模式与sping.net表达式的结合应用(金融里经常需要用到公式,这个公式是抽象的需要自己解释)

原文:http://www.cnblogs.com/kexb/p/6262132.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!