本教程涵蓋了1.8發佈版本對linq查詢的支持。html
開始本教程以前,你應該至少閱讀下C#驅動教程關於C#驅動的介紹數組
首先,添加下面命名空間到您的程序中:服務器
using MongoDB.Driver.Linq;
而後,聲明一變量保存對集合的引用測試
var collection = database.GetCollection<TDocument>("collectionname");
最基本調用linq查詢的方式是構造一個集合變量,經過調用AsQueryable<TDocument>() 後,你即可以正常調用linq了。spa
實例:翻譯
var query = from e in collection.AsQueryable<Employee>() where e.FirstName == "John" select e; foreach (var employee in query) { // do something }
固然,你也能夠經過lambda語法寫查詢表達式,先前的查詢語句等同於下面的寫法:code
var query = collection.AsQueryable<Employee>() .Where(e => e.FirstName == "John");
C#編譯器會在內部把全部查詢翻譯爲lambda句法,因此這兩種寫法沒有優略之分,當你須要的時候(好比某些查詢操做符不被支持的時候),你甚至能夠混用這兩種方式。htm
本教程實例中全部代碼均會展現linq查詢表達式和lamdba表達式(在查詢操做符被支持的前提下).對象
只有linq查詢能夠轉化爲相應的MongoDB查詢時該查詢纔會被支持解析,若是你寫的linq查詢不能被轉化成相應的MongoDB查詢,那麼您的程序會在產生異常或者錯誤。blog
本節介紹支持的LINQ查詢操做符。
不含謂詞的Any只是測試集合中是否存在any文檔對象(any直接引用過來,你們都明白)
var result = (from c in collection.AsQueryable<C>() select c) .Any(); // 或者 var result = collection.AsQueryable<C>() .Any();
含有謂詞的Any用來測試集合中是否存在匹配的文檔,匹配邏輯在謂詞中
var result = (from c in collection.AsQueryable<C>() select c) .Any(c => c.X == 1); // or var result = collection.AsQueryable<C>() .Any(c => c.X == 1);
投影操做後,帶有謂詞的Any是不被支持的(至少當前版本),因此下面代碼是不可用的。
var result = collection.AsQueryable<C>() .Select(c => c.X) .Any(x => x == 1);
一般來講,你能夠使用where字句來替代投影操做,這樣你能夠移除投影操做。
不帶謂詞的Count只是返回文檔對象在集合中數量。
var result = (from c in collection.AsQueryable<C>() select c) .Count(); // 或者 var result = collection.AsQueryable<C>() .Count();
帶有謂詞的Count返回謂詞匹配的文檔數量。
var result = (from c in collection.AsQueryable<C>() select c) .Count(c => c.X == 1); // or var result = collection.AsQueryable<C>() .Count(c => c.X == 1);
說明:謂詞一樣能夠經過where字句和不帶謂詞的Count替代,因此上面實例也能夠這樣寫:
var result = (from c in collection.AsQueryable<C>() where c.X == 1 select c) .Count(); // or var result = collection.AsQueryable<C>() .Where(c => c.X == 1) .Count();
含有謂詞的Count一樣不支持投影后操做,因此下面寫法是無效的。
var result = collection.AsQueryable<C>() .Select(c => c.X) .Count(x => x == 1);
解決方案和Any同樣。
Distinct 返回集合中文檔對象字段或者屬性的惟一值,你能夠投影后經過它過濾重複值。
var result = (from c in collection.AsQueryable<C>() select c.X) .Distinct(); // or var result = collection.AsQueryable<C>() .Select(c => c.X) .Distinct();
投影必須選擇一個特定的字段或屬性的文件。若是該字段或屬性的值是在MongoDB中表示,做爲一個數組,你也能夠使用數組索引從數據中選擇一項:
var result = (from c in collection.AsQueryable<C>() select c.A[i]) .Distinct(); // or var result = collection.AsQueryable<C>() .Select(c => c.A[i]) .Distinct();
ElementAt 從結果集中返回一個特定的文檔,一般要和排序操做一塊兒使用
var result = (from c in collection.AsQueryable<C>() where c.X > 0 orderby c.X select c) .ElementAt(index); // or var result = collection.AsQueryable<C>() .Where(c => c.X > 0) .OrderBy(c => c.X) .ElementAt(index);
若是結果集中文檔對象數量少於ElementAt 中索引,會報出異常。
ElementAtOrDefault 和ElementAt 相似,區別在於當集合中對象少於Index時前者返回null而不是報出異常。
First 返回集合中第一個對象,一般和排序一塊兒使用。
var result = (from c in collection.AsQueryable<C>() where c.X > 0 orderby c.X select c) .First(); // or var result = collection.AsQueryable<C>() .Where(c => c.X > 0) .OrderBy(c => c.X) .First();
若是集合爲空,則First拋出異常
此重載容許你提供謂詞邏輯給First,至關於使用where字句的first查詢。
var result = (from c in collection.AsQueryable<C>() orderby c.X select c) .First(c => c.X > 0); // or var result = collection.AsQueryable<C>() .OrderBy(c => c.X) .First(c => c.X > 0);
First (含有謂詞)一樣不支持投影后操做,因此下面代碼是無效的:
var result = collection.AsQueryable<C>() .OrderBy(c => c.X) .Select(c => c.X) .First(x => x > 0);
解決方案一樣和Any同樣
若是集合爲空,一樣會拋出異常
FirstOrDefault 和First 不一樣之處在於,當集合爲空時,不會拋出異常,而是返回null
FirstOrDefault (含謂詞)和First(含謂詞)用法同樣,不一樣之處在於,集合爲空時,返回null不會拋出異常
Last 從結果集中返回最後一個文檔對象,和First相對,一般和排序操做一塊兒使用:
var result = (from c in collection.AsQueryable<C>() where c.X > 0 orderby c.X select c) .Last(); // or var result = collection.AsQueryable<C>() .Where(c => c.X > 0) .OrderBy(c => c.X) .Last();
若是集合爲空,會拋出異常。
此重載容許你傳遞謂詞邏輯做爲參數給Last,和不帶謂詞的Last操做加上where字句至關。
var result = (from c in collection.AsQueryable<C>() orderby c.X select c) .Last(c => c.X > 0); // or var result = collection.AsQueryable<C>() .OrderBy(c => c.X) .Last(c => c.X > 0);
Last 一樣不支持投影后操做,因此下面寫法是無效的:
var result = collection.AsQueryable<C>() .OrderBy(c => c.X) .Select(c => c.X) .Last(x => x > 0);
解決方案和Any同樣。
若是集合爲空,會拋出異常
LastOrDefault 和 Last 不一樣之處在於,前者當集合爲空時不會拋出異常,只是返回null
LastOrDefault(含謂詞)和 Last (含謂詞)用法同樣,不一樣之處在於前者在集合爲空時返回null,不會拋出異常。
LongCount 用法和Count 同樣,不一樣之處在於返回值前者是64位長整型,後者是32位。
LongCount (含謂詞)和Count (含謂詞)用法同樣,不一樣之處在於返回值前者是64位長整型,後者是32位。
Max 返回集合中文檔對象屬性或者字段值中的最大值,你能夠篩選出投影操做識別出的字段或者屬性的最大值
var result = (from c in collection.AsQueryable<C>() select c.X) .Max(); // or var result = collection.AsQueryable<C>() .Select(c => c.X) .Max();
投影必須選擇一個特定的字段或屬性的文件。若是該字段或屬性的值是在MongoDB中表示,做爲一個數組,你也能夠使用數組索引從數據中選擇一項:
var result = (from c in collection.AsQueryable<C>() select c.A[i]) .Max(); // or var result = collection.AsQueryable<C>() .Select(c => c.A[i]) .Max();
此Max 重載可讓你直接傳遞選擇參數到Max來篩選最大值,能夠用來代替在投影后進行Max操做:
var result = (from c in collection.AsQueryable<C>() select c) .Max(c => c.X); // or var result = collection.AsQueryable<C>() .Max(c => c.X);
Min 返回集合中文檔對象屬性或者字段值中的最小值,你能夠篩選出投影操做識別出的字段或者屬性的最小值
var result = (from c in collection.AsQueryable<C>() select c.X) .Min(); // or var result = collection.AsQueryable<C>() .Select(c => c.X) .Min();
投影必須選擇一個特定的字段或屬性的文件。若是該字段或屬性的值是在MongoDB中表示,做爲一個數組,你也能夠使用數組索引從數據中選擇一項:
var result = (from c in collection.AsQueryable<C>() select c.A[i]) .Min(); // or var result = collection.AsQueryable<C>() .Select(c => c.A[i]) .Min();
此Min 重載可讓你直接傳遞選擇參數到Max來篩選最大值,能夠用來代替在投影后進行Max操做:
var result = (from c in collection.AsQueryable<C>() select c) .Min(c => c.X); // or var result = collection.AsQueryable<C>() .Min(c => c.X);
OfType操做符會向查詢插入一個鑑別器以便你更精確的查詢文檔對象
var result = (from c in collection.AsQueryable<C>().OfType<D>() select c) // or var result = collection.AsQueryable<C>() .OfType<D>();
OrderBy 用於指定結果集升序排序順序
var query = from c in collection.AsQueryable<C>() orderby c.X select c; // or var query = collection.AsQueryable<C>() .OrderBy(c => c.X);
OrderByDescending 用於指定結果集降序排序順序
var query = from c in collection.AsQueryable<C>() orderby c.X descending select c; // or var query = collection.AsQueryable<C>() .OrderByDescending(c => c.X);
Select 用於從匹配文檔中選出一個新類型的結果集。Select 必須爲最後一個操做(除了如 Distinct, Max 和 Min等)
注意:
Select 不會減小從服務器返回的文檔對象字段或者屬性,完整的文檔對象仍是會被返回的,而後才調用Select 方法,所以投影是在「客戶端」的。
var query = from c in collection.AsQueryable<C>() select new { c.X, c.Y }; // or var query = collection.AsQueryable<C>() .Select(c => new { c.X, c.Y });
Single 從結果集中返回第一個也是惟一的文件
var result = (from c in collection.AsQueryable<C>() where c.X > 0 orderby c.X select c) .Single(); // or var result = collection.AsQueryable<C>() .Where(c => c.X > 0) .OrderBy(c => c.X) .Single();
若是結果集爲空或者存在多個文檔,Single 會拋出異常。
此重載能夠傳遞參數到Single ,等同於不含謂詞的Single 加上where字句。
var result = (from c in collection.AsQueryable<C>() orderby c.X select c) .Single(c => c.X > 0); // or var result = collection.AsQueryable<C>() .OrderBy(c => c.X) .Single(c => c.X > 0);
Single 一樣不支持投影后操做,因此下面代碼是無效的:
var result = collection.AsQueryable<C>() .OrderBy(c => c.X) .Select(c => c.X) .Single(x => x > 0);
解決方案和Any同樣。
若是結果集爲空或者存在多個文檔,Single 會拋出異常
SingleOrDefault 和Single 用法同樣,不一樣之處在於當集合爲空或者存在多個文檔對象時,會返回null,而不是拋出異常。
SingleOrDefault(含謂詞) 和Single (含謂詞)用法同樣,不一樣之處在於當集合爲空或者存在多個文檔對象時,會返回null,而不是拋出異常。
使用Skip ,指定從結果集開始跳過多少文件。一般狀況下,你將結合排序操做使用。
var query = (from c in collection.AsQueryable<C>() orderby c.X select c) .Skip(100); // or var query = collection.AsQueryable<C>() .OrderBy(c => c.X) .Skip(100);
使用Take 指定多少文件從服務器返回。結合Skip 使用時,每每你會指定一個排序順序。
var query = (from c in collection.AsQueryable<C>() orderby c.X select c) .Skip(100) .Take(100); // or var query = collection.AsQueryable<C>() .OrderBy(c => c.X) .Skip(100) .Take(100);
ThenBy 是用來指定一個額外的升序排序的結果集。
var query = from c in collection.AsQueryable<C>() orderby c.X, c.Y select c; // or var query = collection.AsQueryable<C>() .OrderBy(c => c.X) .ThenBy(c => c.Y);
ThenByDescending 是用來指定一個額外的降序排序的結果集。
var query = from c in collection.AsQueryable<C>() orderby c.X, c.Y descending select c; // or var query = collection.AsQueryable<C>() .OrderBy(c => c.X) .ThenByDescending(c => c.Y);
WHERE子句用於指定返回知足條件查詢結果。 WHERE子句是將表達查詢文檔類型映射到一個布爾值句法。若是表達式返回true則結果匹配到結果集中。
var query = from c in collection.AsQueryable<C>() where c.X > 0 select c; // or var query = collection.AsQueryable<C>() .Where(c => c.X > 0);
有時也能夠使用多個where字句,其左右至關於&&操做符
例如,下面的查詢是等價的:
var query = (from c in collection.AsQueryable<C>() where c.X > 0 where c.Y > 0) .First(c.Z > 0); // or var query = (from c in collection.AsQueryable<C>() where c.X > 0 && c.Y > 0 && c.Z > 0) .First();
先到此爲止,下節是
支持的where字句