Owais Ahmed Owais Ahmed - 3 years ago 109
JSON Question

C# parse JSON group by type

This is the JSON

[
{
"name": "TeamA",
"zone": "North",
"id": 12,
"players": [
{
"name": "TAPlayer1",
"type": "Keeper"
},
{
"name": "TAPlayer2",
"type": "Bowler"
}
]
},
{
"name": "TeamB",
"zone": "South",
"id": 20,
"players": [
{
"name": "TBPlayer1",
"type": "Keeper"
}
]
},
{
"name": "TeamC",
"zone": "South",
"id": 45,
"players": null
},
{
"name": "TeamD",
"zone": "North",
"id": 40,
"players": [
{
"name": "Tom",
"type": "Keeper"
},
{
"name": "Max",
"type": "Keeper"
},
{
"name": "Sam",
"type": "Bowler"
},
{
"name": "Jim",
"type": "Keeper"
}
]
}
]


I want the result like that (Group by Zone with player type keeper)

North
TAPlayer1
Tom
Max

South
TBPlayer1


I tried to parse like that

public class Player
{
public string name { get; set; }
public string type { get; set; }
}

public class Teams
{
public string name { get; set; }
public string zone { get; set; }
public int id { get; set; }
public List<Player> players { get; set; }
}
Teams[] ownersArray = JsonConvert.DeserializeObject<Teams[]>(json);


I want to display the results group by Zone and type should be keeper. Any suggestions would be appreciated.

Thanks in advance.

Answer Source

After deserializing the JSON

Teams[] teams = JsonConvert.DeserializeObject<Teams[]>(json);

you can use LINQ to group by Zone

var groupedByZone = teams.Where(t => t.players != null).GroupBy(t => t.zone);

From each group we want to get the players

var players = groupedByZone.Select(g => new { 
    name = g.Key, 
    players = g.SelectMany(t => t.players).Where(p => p.type == "Keeper").ToArray() 
});

This could all be done in one statement

var keepersByZone = teams.Where(t => t.players != null)
                         .GroupBy(team => team.zone)
                         .Select(g => new { 
                             name = g.Key, 
                             players = g.SelectMany(team => team.players)
                                        .Where(player => plapyer.type == "Keeper")
                                        .OrderBy(player => player.name)
                                        .ToArray() 
                         });

Show output

foreach(var zone in keepersByZone) {
    Console.WriteLine(zone.name);
    foreach(var player in zone.players) {
        Console.WriteLine(player.name);
    }
    Console.WriteLine();
}
Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download