接續[上篇之預告]
本篇來講講,如何根據前面設計的查詢描述器構造出可執行的運算式,正如標題所示,實作手段將采用Expression Lambda技術,
先來看看主角System.Linq.Expressions.Expression 長什么樣,都有些什么東西,能做什么, 先看看它的類圖:
-
System.Linq.Expressions.ConstantExpression 常量
-
System.Linq.Expressions.DefaultExpression 默認值
-
System.Linq.Expressions.IndexExpression 索引
-
System.Linq.Expressions.MemberExpression 成員(屬性或欄位)
-
System.Linq.Expressions.MethodCallExpression 方法呼叫
-
System.Linq.Expressions.ParameterExpression 引數
-
System.Linq.Expressions.UnaryExpression 一元運算
-
System.Linq.Expressions.BinaryExpression 二元運算
-
System.Linq.Expressions.LambdaExpression 委托
我們主要使用Expression這個類,它包含各種節點型別的 static工廠方法,特別是以下這些方法,對應了查詢需要用到的邏輯、比較、數學,等各種運算操作,
| 邏輯運算 | |
|---|---|
| AndAlso(Expression, Expression) | 表示And邏輯運算 |
| OrElse(Expression, Expression) | 表示Or邏輯運算 |
| 比較運算 | |
| LessThan(Expression, Expression) | 表示小于:"<" |
| LessThanOrEqual(Expression, Expression) | 表示大于等于:“<=" |
| GreaterThan(Expression, Expression) | 表示大于:”>“ |
| GreaterThanOrEqual(Expression, Expression) | 表示大等于:”>=" |
| Equal(Expression, Expression) | 表示等于:”=“ |
| NotEqual(Expression, Expression) | 表示不等于:”!=" |
| IsTrue(Expression) | 測驗運算式結果是否為“True" |
| IsFalse(Expression) | 測驗運算式結果是否為“False" |
| Not(Expression) | 表示”Not" |
| 數學運算 | |
| Add(Expression, Expression) | 加法 |
| Subtract(Expression, Expression) | 減法 |
| Multiply(Expression, Expression) | 乘法 |
| Divide(Expression, Expression) | 除法 |
| Modulo(Expression, Expression) | 模除 |
| Power(Expression, Expression) | 冪運算 |
| 一些操作 | |
| Parameter(Type) | 包裝一個型別為Type的引數 |
| Call(Expression, MethodInfo, Expression, Expression) | 包裝一個方法呼叫 |
| Bind(MemberInfo, Expression) | 包裝一個成員系結,(屬性或欄位) |
| Quote(Expression) | 包裝一個括號 |
| MakeUnary(ExpressionType, Expression, Type) | 包裝一個一元運算 |
| MakeBinary(ExpressionType, Expression, Expression) | 包裝一個二元運算 |
| TypeAs(Expression, Type) | 包裝一個顯式參考或裝箱轉換,其中如果轉換失敗則提供“null”, |
| Coalesce(Expression, Expression, LambdaExpression) | 包裝表示給定轉換函式的聚結操作, |
| 變數、常量、欄位、屬性 | |
| Default(Type) | 包裝一個指定型別的默認值 |
| Constant(Object, Type) | 包裝一個常量 |
| Assign(Expression, Expression) | 賦值操作 |
| Variable(Type, String) | 包裝一個變數定義 |
| Property(Expression, MethodInfo) | 包裝一個屬性 |
| Field(Expression, FieldInfo) | 包裝一個欄位 |
| PropertyOrField(Expression, String) | 包裝一個指定名稱的欄位或屬性 |
| 要的就是這結果 | |
| Lambda(Expression, ParameterExpression[]) | 包裝一個委托,帶有一個引數運算式陣列, |
以上僅列出了一部分,它涵蓋了全部可能要使用到的函式,陳述句,欲詳細了解可以直接乘坐火箭到微軟官方網站查看,
這此函式或功能是有了,如何使用呢?來看個例子:將SQL:Table1.A > 5 and Table1.B=3,轉成(Table1)=>Table1.A > 5 && Table1.B==3;
在Expression的世界里一切都是Expression,因此首先要將Table1、A、5、B、 3先包裝成Expression:
- 開干之前先談個物件
//物體類:
public class Table
{
public int A;
public int B;
}
- 然后包裝各種
Expression
?
//將Table1包裝成ParameterExpression:
var p=Expression.Parameter(typeof(Table1),"Table1");
?
//將5、3這兩個常量包裝成ConstantExpression:
var num5=Expression.Constant(5,typeof(int));
var num3=Expression.Constant(3,typeof(int));
?
//將兩個屬性包裝成MemberExpression,
var a=Expression.PropertyOrField(p,"A")
var b=Expression.PropertyOrField(p,"B")
?
//構造Table1.A>5:
var gt=Expression.GreaterThen(a,num5);
//構造Table1.A=3:
var eq=Expression.Equal(b,num3);
?
- 再構造兩個比較式
//構造Table1.A>5:
var gt=Expression.GreaterThen(a,num5);
//構造Table1.A=3:
var eq=Expression.Equal(b,num3);
- 加上邏輯
And將兩個比較式連接起來
//構造Table1.A>5 && Table1.A=3
var exp=Expression.AndAlso(gt,eq);
- 結果就要出來了
//結果就獲得了:
var lambda=Expression.Lambda()
- 來來來,測驗一下康康接果:
/*===============來來來,測驗一下:===============*/
var f=lambda.Compile();
var x=f.DynamicInvoke(new Table(){A=6,B=3});
var y = f.DynamicInvoke(new Table() { A = 2, B = 3 });
Console.WriteLine("x:{0}\ny:{1}",x,y);
Console.WriteLine("Lambda:{0}",lambda.ToString());
/*輸出:
結果對嗎?我也不知道,我擼得這么辛苦,先讓電腦休息一下,各位看官只要Ctrl+C,Ctrl+V就可以看到了.
*/
- OK,其它各種操作,只要依葫蘆畫瓢便大功可成! 先爽一下!
- 好,暫且爽到這里,欲看如何把括號弄成俄羅斯套娃,且看下回分解.
- 隨手點個贊,讓我也爽爽,可好!
轉載請註明出處,本文鏈接:https://www.uj5u.com/ruanti/553552.html
標籤:架構設計
上一篇:什么是一致性哈希?一致性哈希是如何作業的?如何設計一致性哈希?
下一篇:返回列表
