在List <T>上使用Take(...)时,是否在应用Take(...)之前返回了整个列表?

Abo*_*IRS 4 .net c# linq optimization

我有一个List类型的元素

    public class FriendList 
    {
        public List<string> friends { get; set; } // List of friends names
        public DateTime timestamp { get; set; } // date/time on the data file
    }
Run Code Online (Sandbox Code Playgroud)

我需要一个程序来获得前2个排序timestamp(然后用它们做一些其他的东西).所以我开始写的是

    public void CompareLastTwo ( )
    {
        if ( this._fhist.Count < 2 )
        {
            Console.WriteLine("Need at least two instances of Facebook profile data in the Data folder");
        }

        FriendList latest, secondLatest; 
        if ( this._fhist[0].timestamp > this._fhist[1].timestamp )
        {
            latest = this._fhist[0];
            secondLatest = this._fhist[1];
        }
        else
        {
            latest = this._fhist[1];
            secondLatest = this._fhist[0];
        }

        for ( int i = 2, n = this._fhist.Count; i < n; ++i )
        {
            if ( this._fhist[i].timestamp > latest.timestamp )
            {
                secondLatest = latest;
                latest = this._fhist[i];
            }
            else if ( this._fhist[i].timestamp > secondLatest.timestamp && this._fhist[i].timestamp <= latest.timestamp )
            {
                secondLatest = this._fhist[i];
            }
        }

        // ... 

    }
Run Code Online (Sandbox Code Playgroud)

但后来我意识到如何在C#中获取列表的前N个元素?我能做到的

List<FriendList> latestTwoFriendLists = this._fhist.OrderBy(L => L.timestamp).Take(2);
Run Code Online (Sandbox Code Playgroud)

哪个更紧凑,但它是否有效 ???? 或者计算方程右侧的过程是否Take在前2个之前得到整个有序列表?

Mar*_*zek 7

OrderByTake请求第一项时将整个集合排序.

所以整个LINQ查询将是O(n*log(n)),而不是像现有代码那样的O(n).

  • 是的,但在这种情况下,最好使用更紧凑和明显的代码片段,直到它成为瓶颈. (4认同)
  • 它不会在返回迭代器之前对集合进行排序.在返回迭代器之前,它只执行null检查参数.它**在要求第一个项目时需要对整个集合进行排序.这是一个重要的区别. (4认同)