我想制作IEnumerable<T>
的副本,其中给定索引处的单个项目已被给定值替换。
我定义了以下方法,它可以满足我的需求:
public static IEnumerable<T> ReplaceAt<T>(this IEnumerable<T> source, T item, int index)
{
foreach (T before in source.Take(index))
{
yield return before;
}
yield return item;
foreach (T after in source.Skip(index + 1))
{
yield return after;
}
}
然而,尽管可能很容易理解,但似乎效率低下。创建两个迭代器,其中一个迭代器跳过第一个迭代器已经占用的项目。
有没有更好的方法来定义它?
答案 0 :(得分:2)
怎么样:
public static IEnumerable<T> ReplaceAt<T>(this IEnumerable<T> source, T item, int index)
{
return source.Select((value, i) => index == i ? item : value);
}
答案 1 :(得分:2)
不确定效率,但你试过这个吗?
public static IEnumerable<T> ReplaceAt<T>(this IEnumerable<T> source, T item, int index)
{
return source.Select((x, i) => i == index ? item : x);
}
答案 2 :(得分:1)
如果您想发疯,可以手动展开foreach
:
public static IEnumerable<T> ReplaceAt<T>(this IEnumerable<T> source, T item, int index)
{
int itemIndex = 0;
using(var iter = source.GetEnumerator())
{
while(iter.MoveNext())
{
yield return itemIndex++ == index ? item : iter.Current;
}
}
}