如何将此IEnumerable<KeyValuePair<MyType, IEnumerable<OtherType>>>
转换为新版本
相同类型的序列,除了我只想要值(First()
)中的IEnumerable<OtherType>
。像这样的东西(伪代码):
var toReturn = from kv in source
let k = new KeyValuePair(kv.Key, kv.Value.First())
select k;
答案 0 :(得分:9)
我不确定您是否希望新KeyValuePair中的Value是该类型或单个元素的可枚举。这是两个版本
IEnumerable版本
var toReturn = source.Select(x => new KeyValuePair<SomeType,IEnumerable<SomeOtherType>>(x.Key, x.Value.Take(1));
非可枚举版
var toReturn = source.Select(x => new KeyValuePair<SomeType,SomeOtherType>(x.Key,x.Value.First());
答案 1 :(得分:7)
您所缺少的是要使用的KeyValuePair的类型。您可以使用Jared的lambda表达式版本,或者如果您喜欢查询表达式语法:
var toReturn = from kv in source
select new KeyValuePair<MyType, OtherType>(kv.Key,
kv.Value.First());
如果您不想显式指定类型参数,可以创建自己的帮助器类并使用类型推断:
// Non-generic helper class.
public static class KeyValuePair
{
public static KeyValuePair<TKey, TValue> Of(TKey key, TValue value)
{
return new KeyValuePair<TKey, TValue>(key, value);
}
}
此时您的查询将变为:
var toReturn = from kv in source
select KeyValuePair.Of(kv.Key, kv.Value.First());
或
var toReturn = source.Select(kv => KeyValuePair.Of(kv.Key, kv.Value.First());
编辑:哎呀 - 我想我也误解了你的问题。如果您希望它具有完全相同的类型,即值也可以枚举,请使用Take(1)
代替First()
:
var toReturn = source.Select(kv => KeyValuePair.Of(kv.Key, kv.Value.Take(1));
(不是类型推断可爱吗?:)
答案 2 :(得分:1)
var toReturn = source
.ToDictionary(
kvp => kvp.Key,
kvp => kvp.Value.Take(1)
);
答案 3 :(得分:0)
为什么要获得相同类型的集合?当您拥有第一个元素时,您不需要集合(IEnumerable<OtherType>
),只需要一个值(OtherType
)。
这(就像你发布的那个)应该是正确的(你只需要为KeyValuePair添加通用参数)
var toReturn = from kv in source select new KeyValuePair<SomeType, OtherType>(kv.Key, kv.Value.First());
如果你真的想要获得相同类型的集合,请写
var toReturn = from kv in source select new KeyValuePair<SomeType, IEnumerable<OtherType>>(kv.Key, new [] { kv.Value.First() });
注意:当您将其包装到通用函数中时,不需要为KeyValuePair提供显式类型参数。
KeyValuePair<TKey, TValue> Pair<TKey, TValue>(TKey key, TValue value) {
return new KeyValuePair<TKey, TValue>(key, value);
}
//
var foo = Pair(1, "Hello");