public class ConsolidatedChild
{
public string School { get; set; }
public string Friend { get; set; }
public string FavoriteColor { get; set; }
public List<Child> Children { get; set; }
}
public class Child
{
public string School { get; set; }
public string Name { get; set; }
public string Address { get; set; }
public string Friend { get; set; }
public string Mother { get; set; }
public string FavoriteColor { get; set; }
}
鉴于以上两个类,我想使用LINQ从列表中创建一个列表,该列表按School,Friend和FavoriteColor属性进行分组。
请忽略属性,编写代码只是为了帮助解决这个问题。
#1 楼
容易:var consolidatedChildren =
from c in children
group c by new
{
c.School,
c.Friend,
c.FavoriteColor,
} into gcs
select new ConsolidatedChild()
{
School = gcs.Key.School,
Friend = gcs.Key.Friend,
FavoriteColor = gcs.Key.FavoriteColor,
Children = gcs.ToList(),
};
var consolidatedChildren =
children
.GroupBy(c => new
{
c.School,
c.Friend,
c.FavoriteColor,
})
.Select(gcs => new ConsolidatedChild()
{
School = gcs.Key.School,
Friend = gcs.Key.Friend,
FavoriteColor = gcs.Key.FavoriteColor,
Children = gcs.ToList(),
});
评论
假设我在分组依据中有很多属性,是否有更干净的方法来列出所有属性?
– Guiomie
15年8月21日在18:35
@guiomie-我不会说有一种更清洁的方法。您可以将对象序列化为单个字符串并在其上分组,但这将需要在其他地方添加更多代码。因此,在我看来,无论有多少属性,此答案都是最干净的方法。
–谜题
15年8月21日在23:03
@Doppelganger-我回滚您的编辑有两个原因。选择使用最后一个逗号(在FavoriteColor之后)是有目的的-这是合法的语法,它使代码重构更加容易。使用gcs而不是gc进行分组变量的选择也是有目的的-它向我表明这是“许多c的组”。
–谜题
15年11月28日在1:05
我以为肯定不会编译,但是您绝对正确。至于重命名变量,那仅仅是为了超过六个字符的限制。我从不喜欢弄乱某人的变量名。无论如何,再次感谢您的出色回答!
–Doppelganger
2015年11月30日20:16
@AlexanderRyanBaggett-完成。
–谜题
19年2月12日在22:17
#2 楼
给定一个列表:var list = new List<Child>()
{
new Child()
{School = "School1", FavoriteColor = "blue", Friend = "Bob", Name = "John"},
new Child()
{School = "School2", FavoriteColor = "blue", Friend = "Bob", Name = "Pete"},
new Child()
{School = "School1", FavoriteColor = "blue", Friend = "Bob", Name = "Fred"},
new Child()
{School = "School2", FavoriteColor = "blue", Friend = "Fred", Name = "Bob"},
};
查询如下:
var newList = list
.GroupBy(x => new {x.School, x.Friend, x.FavoriteColor})
.Select(y => new ConsolidatedChild()
{
FavoriteColor = y.Key.FavoriteColor,
Friend = y.Key.Friend,
School = y.Key.School,
Children = y.ToList()
}
);
测试代码:
foreach(var item in newList)
{
Console.WriteLine("School: {0} FavouriteColor: {1} Friend: {2}", item.School,item.FavoriteColor,item.Friend);
foreach(var child in item.Children)
{
Console.WriteLine("\t Name: {0}", child.Name);
}
}
结果:
School: School1 FavouriteColor: blue Friend: Bob
Name: John
Name: Fred
School: School2 FavouriteColor: blue Friend: Bob
Name: Pete
School: School2 FavouriteColor: blue Friend: Fred
Name: Bob
评论
对于那些喜欢流畅界面的人。一个小小的错误:对于新用户来说,在两个Func定义中使用相同的变量“ x”并不是很清楚。我建议更改为与上面的匹配,其中“ c”是子级,“ gcs”是分组的子级。
–迈克尔·布莱克本
2012年11月19日15:46
@jazmatician _我同意您的观点,即重复使用x可能会使某些人混淆,但对于变量名的选择却没有。我将其更改为x和y进行微分。
–贾米茨
2012年11月19日15:51
变量名也不是我的选择。实际上,在撰写本文时,我努力弄清楚“ gcs”对作者的意义。我能想到的最好的是“ CS组”。无论如何,我仅推荐它尝试使某人易于在两种语法之间建立思维导图。 (句法?我敢打赌语法是那些单词中的一个,它是自己的复数形式。因为这是英文,所以“语法”为什么要服从关于复数的句法规则?)
–迈克尔·布莱克本
2012年11月19日下午16:51
回答我自己的切线:en.wiktionary.org/wiki/syntax
–迈克尔·布莱克本
2012年11月19日下午16:51
我不同意迈克尔的这一观点。我认为x应该在两个地方都使用。唯一不应该的情况是将Func与另一个Hunc一起使用时,应转到y。否则会造成混乱。
–塞尔吉·萨根(Serj Sagan)
14年10月30日在16:17
评论
对的,这是可能的。看一下这篇文章中提供的示例。这是另一个很好的例子stackoverflow.com/questions/15605468 / ...