簡體   English   中英

使用linq從列表列表中獲取n個項目

[英]Get n items from list of list using linq

我有一個包含其他用戶/播放器列表的列表。 這些用戶按照他們的特定范圍的高爾夫障礙進行分組和分類。 例如,內部列表包含的索引

[0] =>計數2(玩家)

1 =>計數3(玩家)

[2] =>計數1(玩家)

為了在錦標賽中進行飛行,這些玩家/用戶被分組為每次飛行最多3或4個玩家。 我如何根據指定的限額填寫每個航班。 零索引包含2個玩家,因此我必須從下一個索引中減去其余2個玩家,依此類推以補償玩家。

對於上述所有情況,我試圖使用LINQ查詢執行此類功能,但無法解決。 下面是我嘗試過的。

List<List<Models.User>> PlayerSortedList = new List<List<Models.User>>(); //contains all the grouped players 

foreach (var item in PlayerSortedList)
{
var extraPlayers = new List<Models.User>();

if (item.Count != Convert.ToInt16(vm.flight.PlayerLimit))
{
//Take extra players from next list and remove players from the next list
 int limit = Convert.ToInt16(vm.flight.PlayerLimit) - item.Count;
 var players = PlayerSortedList.Skip(i); // this has not skipped the first index


 extraPlayers = (from player in players
 from p in player
 where player.Count > 0
 orderby (p.UserHandicap).Take(limit)
 select p).ToList(); // generating error as must be icomparable but i dont 
 have to compare anything, but take out players from the next items in the list
}

通過從列表中的下一個項目中抽出額外的玩家,我確實必須將它們添加到上一個列表中,並從我已刪除的列表中刪除那些玩家。

在此處輸入圖片說明

那這個呢?

    static void Main(string[] args)
    {
        var listOfListOfPlayers = new List<List<Player>>();
        //Flatten the list, so not having to deal with lists of lists
        var allPlayers = listOfListOfPlayers.SelectMany(l => l).ToList();
        //Count the players that can not take part of a flight
        var playersNotFittingInFlight = allPlayers.Count % 4;
        //The number of players that will be spread in flights
        var maxPlayersInFlights = allPlayers.Count - playersNotFittingInFlight;
        //The number of flights you will end up having
        var maxFlights = maxPlayersInFlights / 4;
        var flights = new List<Flight>(maxFlights);
        //Create the flights with the players
        for (var i=0;i<maxPlayersInFlights; i=i+4)
        {
            var flight = new Flight();
            //Take 4 players everytime.
            var players = allPlayers.Skip(i).Take(4);
            flight.Players.AddRange(players);
            flights.Add(flight);
        }
    }

    public class Flight
    {
        public List<Player> Players { get; set; } = new List<Player>();
    }

    public class Player
    {

    }
}

可以通過使用單個linq查詢來做到這一點。

var limit = 4;
var results = playerSortedList
    // Combine all the users in the lists into a single list
    .SelectMany(l => l) 
    // .SelectMany(l => l.OrderBy(x=>x.Handicap)) // use this in case it is needed to reorder the users within each sub list.

    // Use index of the users within the list to create bucket numbers.
    .Select((user, idx) => new { User = user, Bucket = (idx / limit) })

    // Group the users using the bucket numbers.
    .GroupBy(x => x.Bucket)

    // Make the whole thing a List<List<User>> again.
    .Select(x=>x.Select(bucket => bucket.User).ToList())
    .ToList();

親切的問候,D.

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM