2016-09-02 44 views
0

我對LINQ方法SingleOrDefaultFirstOrDefault,LastOrDefaultElementAtOrDefault方法的預期行爲或系列操作在數據庫上感到困惑。對於數據庫集合,應該FirstOrDefault返回null嗎?

他們是否應該返回:

  1. 空,或
  2. 填充了默認值的新對象?
+0

它們返回['默認(T)'](http://stackoverflow.com/questions/2432909/what-does-defaultobject-do-in-c) –

回答

1

它們返回的項目的順序或項目的default值中,如果序列是空的(或「ElementAtOrDefault」的情況下,如果指定的索引超出範圍)。

的下面摘錄是從文檔default

的解決方案是使用默認的關鍵字,這將返回null爲數字值類型 引用類型和爲零。對於結構體, 將返回結構體的每個成員初始化爲零或空,具體取決於 關於它們是值類型還是引用類型。

鏈接到default文檔:https://msdn.microsoft.com/en-us/library/xwth0h0d.aspx

0

Enumerable.FirstOrDefault

默認(TSource)如果是空的返回值部;否則,來源中的第一個元素。


default(T)Reference Types爲null,在幾乎所有情況,但對於Value Types不爲空。例子:

int i; // 0 
var j = default(int); // 0 
var b = default(bool); // false 
var s = default(string); // null 
var s = default(object); // null 

var i0 = (new int[] { }).FirstOrDefault(); // 0 
var s0 = (new string[] { }).FirstOrDefault(); // null 

還有DefaultIfEmpty

var i1 = new int[] { }.DefaultIfEmpty(-1).ToArray(); // { -1 } 
0

這裏有一些定義的使用反射鏡。

FirstOrDefault

public static TSource FirstOrDefault<TSource>(this IEnumerable<TSource> source) 
{ 
    if (source == null) 
    { 
     throw Error.ArgumentNull("source"); 
    } 
    IList<TSource> list = source as IList<TSource>; 
    if (list != null) 
    { 
     if (list.Count > 0) 
     { 
      return list[0]; 
     } 
    } 
    else 
    { 
     using (IEnumerator<TSource> enumerator = source.GetEnumerator()) 
     { 
      if (enumerator.MoveNext()) 
      { 
       return enumerator.Current; 
      } 
     } 
    } 
    return default(TSource); 
} 

的SingleOrDefault

public static TSource SingleOrDefault<TSource>(this IEnumerable<TSource> source) 
    { 
     if (source == null) 
     { 
      throw Error.ArgumentNull("source"); 
     } 
     IList<TSource> list = source as IList<TSource>; 
     if (list != null) 
     { 
      switch (list.Count) 
      { 
       case 0: 
        return default(TSource); 

       case 1: 
        return list[0]; 
      } 
     } 
     else 
     { 
      using (IEnumerator<TSource> enumerator = source.GetEnumerator()) 
      { 
       if (!enumerator.MoveNext()) 
       { 
        return default(TSource); 
       } 
       TSource current = enumerator.Current; 
       if (!enumerator.MoveNext()) 
       { 
        return current; 
       } 
      } 
     } 
     throw Error.MoreThanOneElement(); 
    } 

LastOrDefault

public static TSource LastOrDefault<TSource>(this IEnumerable<TSource> source) 
    { 
     if (source == null) 
     { 
      throw Error.ArgumentNull("source"); 
     } 
     IList<TSource> list = source as IList<TSource>; 
     if (list != null) 
     { 
      int count = list.Count; 
      if (count > 0) 
      { 
       return list[count - 1]; 
      } 
     } 
     else 
     { 
      using (IEnumerator<TSource> enumerator = source.GetEnumerator()) 
      { 
       if (enumerator.MoveNext()) 
       { 
        TSource current; 
        do 
        { 
         current = enumerator.Current; 
        } 
        while (enumerator.MoveNext()); 
        return current; 
       } 
      } 
     } 
     return default(TSource); 
    } 

ElementAtOrDefault

public static TSource ElementAtOrDefault<TSource>(this IEnumerable<TSource> source, int index) 
    { 
     if (source == null) 
     { 
      throw Error.ArgumentNull("source"); 
     } 
     if (index >= 0) 
     { 
      IList<TSource> list = source as IList<TSource>; 
      if (list != null) 
      { 
       if (index < list.Count) 
       { 
        return list[index]; 
       } 
      } 
      else 
      { 
       using (IEnumerator<TSource> enumerator = source.GetEnumerator()) 
       { 
        while (enumerator.MoveNext()) 
        { 
         if (index == 0) 
         { 
          return enumerator.Current; 
         } 
         index--; 
        } 
       } 
      } 
     } 
     return default(TSource); 
    } 
+0

的源代碼也在這裏可用Enumerable:http://referencesource.microsoft.com/#System.Core/System/Linq/Enumerable.cs,這裏爲IQueryable:http://referencesource.microsoft.com/#System.Core/System/ LINQ/IQueryable.cs – astidham2003