CRL快速開發框架系列教程十三(嵌套查詢)

本系列目錄

  1. CRL快速開發框架系列教程一(Code First數據表不需再關心)
  2. CRL快速開發框架系列教程二(基於Lambda表達式查詢)
  3. CRL快速開發框架系列教程三(更新數據)
  4. CRL快速開發框架系列教程四(刪除數據)
  5. CRL快速開發框架系列教程五(使用緩存)
  6. CRL快速開發框架系列教程六(分佈式緩存解決方案)
  7. CRL快速開發框架系列教程七(使用事務)
  8. CRL快速開發框架系列教程八(使用CRL.Package)
  9. CRL快速開發框架系列教程九(導入/導出數據)
  10. CRL快速開發框架系列教程十(導出對象結構)
  11. CRL快速開發框架系列教程十一(大數據分庫分表解決方案)
  12. CRL快速開發框架系列教程十二(MongoDB支持)
  13. CRL快速開發框架系列教程十三(嵌套查詢)

 正文

像LINQ TO SQL一樣,任意查詢是衆多ORM的終級夢想,一般做個關聯查詢就差不多了,再來嵌套查詢,就很麻煩了

因爲需要語法表達嵌套關係和篩選結果,一般基於Lambda表達式的ORM才能實現(拼串的就算了)

 

CRL4.2版本解決了匿名對象解析和子查詢表達的問題,現在查詢可以任意組合了
爲了兼容以前的寫法,增加了LambdaQuery.SelectV方法,返回LambdaQueryResultSelect類型
同時增加了以下幾種方式

  • 關聯子查詢
    public LambdaQueryViewJoin<T, TJoinResult> Join<TJoinResult>(LambdaQueryResultSelect<TJoinResult> resultSelect, Expression<Func<T, TJoinResult, bool>> expression, JoinType joinType = JoinType.Inner) 
  • 聯合查詢
    public LambdaQueryResultSelect<TResult> Union<TResult2>(LambdaQueryResultSelect<TResult2> resultSelect, UnionType unionType = UnionType.UnionAll)
  • In,Exists查詢也改爲子查詢形式
  • 返回多種結果
    public List<TResult> ToList()//返回匿名對象
    public List<TResult2> ToList<TResult2>()//返回指定類型
    public List<dynamic> ToDynamic()//返回動態類型

爲了使子查詢有關聯性,需要調用CreateQuery方法創建查詢
使用嵌套查詢過程表示爲:

主查詢 => CreateQuery子查詢 => 返回匿名對象篩選LambdaQueryResultSelect => 主查詢嵌套子查詢 => 返回結果

聲明查詢

var query = Code.ProductDataManage.Instance.GetLambdaQuery();
var query2 = query.CreateQuery<Code.Order>();

直接返回匿名結果

var result1 = query.SelectV(b => new { id = b.Id, name = b.CategoryName }).ToList();

SQL

select  t1.[Id] as id,t1.[CategoryName] as name  from [ProductData] t1  with(nolock) 

 

關聯一個子查詢

只要是LambdaQuery創建的語法都支持,如GROUP,DISTINCT,或者已經是一個關聯查詢

var viewJoin = query2.Where(b => b.Id > 10).SelectV(b => b);
var result2 = query.Join(viewJoin, (a, b) => a.UserId == b.UserId).Select((a, b) => new { a.CategoryName, b.OrderId }).ToList();

SQL

select  t1.[CategoryName] as CategoryName,t2.[OrderId] as OrderId  from [ProductData] t1  with(nolock)  
Inner join (select  t2.[Id],t2.[Status],t2.[OrderId],t2.[Remark],t2.[UserId],t2.[Channel],t2.[AddTime]  from [OrderProduct] t2  with(nolock)  where (t2.[Id]>@par0) ) t2
on (t1.[UserId]=t2.[UserId])

  

聯合查詢(支持N個)

var view1 = query.SelectV(b => new { a1 = b.Id, a2 = b.ProductName });
var view2 = query2.SelectV(b => new { a1 = b.Id, a2 = b.Remark });
var result3 = view1.Union(view2).OrderBy(b => b.a1).OrderBy(b => b.a2, false).ToList();

SQL:

select  t1.[Id] as a1,t1.[ProductName1] as a2  from [ProductData] t1  with(nolock)  
union all select t2.[Id] as a1,t2.[Remark] as a2 from [OrderProduct] t2 with(nolock) order by [a1] desc, [a2] asc

 

按In查詢

var view = query2.Where(b => b.Name == "123").SelectV(b => b.Id);
query.In(view, b => b.UserId);
var sql2 = query.PrintQuery();

SQL:

select  t1.[Id],t1.[InterFaceUser],t1.[Date2],t1.[UserId],t1.[BarCode],t1.[TransType]
from [ProductData] t1  with(nolock)  where t1.[UserId] in(select  t2.[Id]  from [Member] t2  with(nolock)  where (t2.[Name]=@par0) ) 

 

來一個複雜的

var q1 = Code.OrderManage.Instance.GetLambdaQuery();
var q2 = q1.CreateQuery<Code.ProductData>();
q2.Where(b => b.Id > 0);
var view = q2.CreateQuery<Code.Member>().GroupBy(b => b.Name).Where(b => b.Id > 0).SelectV(b => new { b.Name, aa = b.Id.COUNT() });//GROUP查詢
var view2 = q2.Join(view, (a, b) => a.CategoryName == b.Name).Select((a, b) => new { ss1 = a.UserId, ss2 = b.aa });//關聯GROUP
q1.Join(view2, (a, b) => a.Id == b.ss1).Select((a, b) => new { a.Id, b.ss1 });//再關聯
var result = view2.ToList();
var sql = q1.ToString();

SQL:

SELECT t1.[Id] AS Id,
       t2.[ss1] AS ss1
FROM [OrderProduct] t1 with(nolock)
INNER JOIN
  (SELECT t2.[UserId] AS ss1,
          t3.[aa] AS ss2
   FROM [ProductData] t2 with(nolock)
   INNER JOIN
     (SELECT t3.[Name] AS Name,
             COUNT(t3.Id) AS aa
      FROM [Member] t3 with(nolock)
      WHERE (t3.[Id]>@par1)
      GROUP BY t3.[Name]) t3 ON (t2.[CategoryName]=t3.[Name])
   WHERE (t2.[Id]>@par0) ) t2 ON (t1.[Id]=t2.[ss1])

  

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章