我有List<IGrouping<string,string>>
。
以某种方式可以将新项目添加到此列表中吗?或者实际上,是否可以创建一些IGrouping对象?
答案 0 :(得分:55)
如果你真的想创建自己的IGrouping<TKey, TElement>
,它是一个简单的实现界面:
public class MyGrouping<TKey, TElement> : List<TElement>, IGrouping<TKey, TElement>
{
public TKey Key
{
get;
set;
}
}
此类继承自List<T>
并实现IGrouping
接口。除了IEnumerable
和IEnumerable<TElement>
(List<T>
满足)的要求之外,唯一要实现的属性是Key
。
从这里,您可以创建所需的所有MyGrouping<string, string>
并将其添加到List<IGrouping<string,string>>
。
答案 1 :(得分:11)
从.NET 4.0开始,BCL中似乎没有任何实现IGrouping<TKey, TElement>
接口的 public 类型,因此您将无法“新建一个“很轻松。”
当然,没有什么可以阻止你:
IGrouping<TKey, TElement>
和ToLookup
等LINQ查询中获取GroupBy
的实例/实例,并将其添加到您的列表中。ToList()
。示例:
IEnumerable<Foo> foos = ..
var barsByFoo = foos.ToLookup(foo => foo.GetBar());
var listOfGroups = new List<IGrouping<Foo, Bar>>();
listOfGroups.Add(barsByFoo.First()); // a single group
listOfGroups.AddRange(barsByFoo.Take(3)); // multiple groups
但是,为什么你想要做到这一点并不清楚。
答案 2 :(得分:5)
您还可以通过不对列表中的内容进行分组来破解分组:
var listOfGroups = new[] { "a1", "a2", "b1" }
.GroupBy(x => x.Substring(0, 1))
.ToList();
// baz is not anything to do with foo or bar yet we group on it
var newGroup = new[] { "foo", "bar" }.GroupBy(x => "baz").Single();
listOfGroups.Add(newGroup);
listOfGroups
然后包含:
a:
a1, a2
b:
b1
baz:
foo, bar
答案 3 :(得分:5)
IGrouping<TKey, TElement> CreateGroup<TKey, TElement>(IEnumerable<TElement> theSeqenceToGroup, TKey valueForKey)
{
return theSeqenceToGroup.GroupBy(stg => valueForKey).FirstOrDefault();
}
答案 4 :(得分:1)
var headers = from header in new[] {
new { Name = "One", List = new[] { "One 1", "One 2", "One 2" } },
new { Name = "Two", List = new[] { "Two 1", "Two 2", "Two 2" } }
} from value in header.List group value by header.Name;
答案 5 :(得分:1)
基于dovid的回答,我创建了以下扩展方法,该方法从IGrouping<TKey, TElement>
和类型为IEnumerable<TElement>
的键创建TKey
的实例:
public static IGrouping<TKey, TElement> ToGroup<TKey, TElement>(
this IEnumerable<TElement> elements,
TKey keyValue)
{
return elements.GroupBy(_ => keyValue).FirstOrDefault();
}
可以这样称呼:
var fruits = new [] { "Apples", "Bananas" };
var myFruitsGroup = fruits.ToGroup("fruitsKey");
请注意,ToGroup()
可以返回null
。
我还创建了另一种GroupBy
扩展方法:
public static IEnumerable<IGrouping<TKey, TElement>> GroupBy<TSource, TKey, TElement>(
this IEnumerable<TSource> source,
Func<TSource, TKey> keySelector,
Func<TSource, IEnumerable<TElement>> elementsSelector)
{
return source
.Select(s => elementsSelector(s)
.ToGroup(keySelector(s)))
.Where(g => g != default(IGrouping<TKey, TElement>));
}
可以这样使用:
var foodItems = new []
{
new { Category = "Fruits", Items = new [] { "Apples", "Bananas" } },
new { Category = "Vegetables", Items = new [] { "Tomatoes", "Broccoli" } },
};
var categoryGroups = foodItems.GroupBy(i => i.Category, i => i.Items);
答案 6 :(得分:-2)
IGrouping
接口用于LINQ中的GroupBy()
运算符。您通常会从带有 IGrouping
子句的LINQ查询中获取group by
对象。但是,拥有一个分组列表没有多大意义。