目录
表达式树练习实践:C# 运算符
在 C# 中,算术运算符,有以下类型
- 算术运算符
- 关系运算符
- 逻辑运算符
- 位运算符
- 赋值运算符
- 其他运算符
这些运算符根据参数的多少,可以分作一元运算符、二元运算符、三元运算符。本文将围绕这些运算符,演示如何使用表达式树进行操作。
对于一元运算符和二元运算符的 Expression
的子类型如下:
UnaryExpression; //一元运算表达式
BinaryExpression; //二元运算表达式
一,算术运算符
运算符 | 描述 |
---|---|
+ | 把两个操作数相加 |
- | 从第一个操作数中减去第二个操作数 |
* | 把两个操作数相乘 |
/ | 分子除以分母 |
% | 取模运算符,整除后的余数 |
++ | 自增运算符,整数值增加 1 |
-- | 自减运算符,整数值减少 1 |
+ 与 Add()
正常代码
int a;
int b;
a = 100;
b = 200;
var ab = a + b;
Console.WriteLine(ab);
使用表达式树构建
ParameterExpression a = Expression.Parameter(typeof(int), "a");
ParameterExpression b = Expression.Parameter(typeof(int), "b");
// ab = a + b
BinaryExpression ab = Expression.Add(a, b);
// 打印 a + b 的值
MethodCallExpression method = Expression.Call(null, typeof(Console).GetMethod("WriteLine", new Type[] { typeof(int) }), ab);
Expression<Action<int, int>> lambda = Expression.Lambda<Action<int, int>>(method, a, b);
lambda.Compile()(100, 200);
Console.ReadKey();
如果想复杂一些,使用 块
来执行:
ParameterExpression a = Expression.Parameter(typeof(int), "a");
ParameterExpression b = Expression.Parameter(typeof(int), "b");
// 别忘记了赋值
BinaryExpression aa = Expression.Assign(a, Expression.Constant(100, typeof(int)));
BinaryExpression bb = Expression.Assign(b, Expression.Constant(200, typeof(int)));
// ab = a + b
BinaryExpression ab = Expression.Add(a, b);
// 打印 a + b 的值
MethodCallExpression method = Expression.Call(null, typeof(Console).GetMethod("WriteLine", new Type[] { typeof(int) }), ab);
// 以块的形式执行代码,相当于{ }
// 不需要纠结这里,后面会有详细说明,重点是上面
var call = Expression.Block(new ParameterExpression[] { a, b }, aa, bb, method);
Expression<Action> lambda = Expression.Lambda<Action>(call);
lambda.Compile()();
上面两个示例,是使用表达式树计算结果,然后还是使用表达式树打印结果。
前者依赖外界传入参数值,赋予 a、b,后者则全部使用表达式树赋值和运算。
那么,如何通过表达式树执行运算,获取执行结果呢?
ParameterExpression a = Expression.Parameter(typeof(int), "a");
ParameterExpression b = Expression.Parameter(typeof(int), "b");
// ab = a + b
BinaryExpression ab = Expression.Add(a, b);
Expression<Func<int, int, int>> lambda = Expression.Lambda<Func<int, int, int>>(ab, a, b);
int result = lambda.Compile()(100, 200);
Console.WriteLine(result);
Console.ReadKey();
这些区别在于如何编写 Expression.Lambda()
。
另外,使用 AddChecked()
可以检查操作溢出。
- 与 Subtract()
与加法一致,此处不再赘述,SubtractChecked()
可以检查溢出。
a - b
,结果是 100 。
ParameterExpression a = Expression.Parameter(typeof(int), "a");
ParameterExpression b = Expression.Parameter(typeof(int), "b");
// ab = a - b
BinaryExpression ab = Expression.Subtract(a, b);
Expression<Func<int, int, int>> lambda = Expression.Lambda<Func<int, int, int>>(ab, a, b);
int result = lambda.Compile()(200, 100);
Console.WriteLine(result);
乘除、取模
乘法
// ab = a * b
BinaryExpression ab = Expression.Multiply(a, b);
// ab = 20000
除法
// ab = a / b
BinaryExpression ab = Expression.Divide(a, b);
// ab = 2
取模(%)
ParameterExpression a = Expression.Parameter(typeof(int), "a");
ParameterE