Ejemplo n.º 1
0
 /// <summary>
 /// 构造函数
 /// </summary>
 /// <param name="variableCoercisonStrategy">默认变量值约束策略</param>
 /// <param name="context">公式执行上下文</param>
 public CSharpFormulaGlobal(
     IVariableCoercionStrategy variableCoercisonStrategy,
     FormulaEvaluatingContext context)
 {
     this.variableCoercisonStrategy = variableCoercisonStrategy;
     this.context = context;
 }
Ejemplo n.º 2
0
        /// <summary>
        /// 执行表达式
        /// </summary>
        /// <param name="formula">表达式</param>
        /// <param name="context">执行上下文</param>
        /// <returns></returns>
        public async Task <double> EvalAsync(string formula, FormulaEvaluatingContext context)
        {
            try
            {
                double result = await CSharpScript.EvaluateAsync <double>(
                    formula,
                    ScriptOptions.Default
                    //.WithImports("System")
                    .WithImports(availableMethodsType.Namespace)
                    .WithReferences(
                        typeof(System.Math).Assembly,
                        typeof(System.Double).Assembly,
                        typeof(Nullable <>).Assembly,
                        typeof(CSharpFormulaGlobal).Assembly,
                        availableMethodsType.Assembly
                        ),
                    new CSharpFormulaGlobal(variableCoercisonStrategy, context)
                    );

                if (Double.IsInfinity(result))
                {
                    throw new DivideByZeroException($"公式 {formula} 发生除数为零异常");
                }
                return(result);
            }
            catch (CompilationErrorException e)
                when(e.Message.Contains("CS0020"))
                {
                    throw new DivideByZeroException($"公式 {formula} 发生除数为零异常");
                }
        }
Ejemplo n.º 3
0
        public async Task DoubleThrowWhenEvalDivideByZeroTest()
        {
            var evaluator       = new CSharpExecutor(typeof(Math), new NullNotAllowedStrategy());
            var fakeVarProvider = A.Fake <IVariableProvider>();
            var context         = new FormulaEvaluatingContext
            {
                VariableProvider = fakeVarProvider
            };
            var formula = "1.0/0";

            await Assert.ThrowsAsync <DivideByZeroException>(() =>
                                                             evaluator.EvalAsync(formula, context)
                                                             );
        }
Ejemplo n.º 4
0
        public async Task EvalNonExistingVariableTest()
        {
            var evaluator       = new CSharpExecutor(typeof(Math), new NullNotAllowedStrategy());
            var fakeVarProvider = A.Fake <IVariableProvider>();

            A.CallTo(() => fakeVarProvider.GetVarAsync("a"))
            .Returns(Task.FromResult <double?>(null));
            var context = new FormulaEvaluatingContext
            {
                VariableProvider = fakeVarProvider
            };
            var formula = "await Var(\"a\") + await Var(\"b\") + 3";

            await Assert.ThrowsAsync <CoerceVariableFailException>(() =>
                                                                   evaluator.EvalAsync(formula, context)
                                                                   );
        }
Ejemplo n.º 5
0
        public async Task IntThrowWhenEvalDivideByZeroTest()
        {
            var evaluator       = new CSharpExecutor(typeof(Math), new NullNotAllowedStrategy());
            var fakeVarProvider = A.Fake <IVariableProvider>();

            A.CallTo(() => fakeVarProvider.GetVarAsync("a"))
            .Returns(0);
            var context = new FormulaEvaluatingContext
            {
                VariableProvider = fakeVarProvider
            };
            var formula = "1/await Var(\"a\")";

            await Assert.ThrowsAsync <DivideByZeroException>(() =>
                                                             evaluator.EvalAsync(formula, context)
                                                             );
        }
Ejemplo n.º 6
0
        public async Task EvalExpressionTest(string formula, double expected)
        {
            //var evaluator = new CSharpExecutor(new NullNotAllowedStrategy());
            //var fakeVarProvider = A.Fake<IVariableProvider>();
            //A.CallTo(() => fakeVarProvider.GetVarAsync("a", A<VariableCriteria>.That.IsNotNull()))
            //    .Returns(10);
            //A.CallTo(() => fakeVarProvider.GetVarAsync("参数", A<VariableCriteria>.That.IsNotNull()))
            //    .Returns(20);
            //A.CallTo(() => fakeVarProvider.GetVarAsync("PI", A<VariableCriteria>.That.IsNotNull()))
            //    .Returns(Math.PI);
            //var context = new FormulaEvaluatingContext
            //{
            //    VariableProvider = fakeVarProvider,
            //    DistrictIndicatorResolver = A.Fake<IDistrictIndicatorResolver>(),
            //};

            //var actual = await evaluator.EvalAsync(formula, context);

            //Assert.Equal(expected, actual);

            var evaluator       = new CSharpExecutor(typeof(Math), new NullNotAllowedStrategy());
            var fakeVarProvider = A.Fake <IVariableProvider>();

            A.CallTo(() => fakeVarProvider.GetVarAsync("a"))
            .Returns(10);
            A.CallTo(() => fakeVarProvider.GetVarAsync("参数"))
            .Returns(20);
            A.CallTo(() => fakeVarProvider.GetVarAsync("PI"))
            .Returns(Math.PI);
            var context = new FormulaEvaluatingContext
            {
                VariableProvider = fakeVarProvider,
                //DistrictIndicatorResolver = A.Fake<IDistrictIndicatorResolver>(),
            };

            var actual = await evaluator.EvalAsync(formula, context);

            Assert.Equal(expected, actual);
        }
Ejemplo n.º 7
0
        /// <summary>
        /// 执行表达式
        /// </summary>
        /// <param name="formula">表达式</param>
        /// <param name="context">执行上下文</param>
        /// <returns></returns>
        public Task <double> EvalAsync(string formula, FormulaEvaluatingContext context)
        {
            var scriptToExecute = interpreter.Interpret(formula, availableMethodsType);

            return(executor.EvalAsync(scriptToExecute, context));
        }
Ejemplo n.º 8
0
 /// <summary>
 /// 从变量源获取原始值
 /// </summary>
 /// <param name="variableName"></param>
 /// <param name="context"></param>
 /// <returns></returns>
 private async Task <double?> GetRawValue(string variableName, FormulaEvaluatingContext context)
 {
     return(await context.VariableProvider.GetVarAsync(variableName));
 }