在 C# 中,如何将我的数组从 IEnumerable<IMyInterface> 转换为 IEnumerable<T>?
In C#, how can I convert my array from IEnumerable<IMyInterface> to IEnumerable<T>?
在 C# 中,我想获取类型为 "T" 的数组,我知道 "T" 支持接口 "IMyInterface" 和:
- 将其转换为 "IMyinterface"
的数组
- 对该数组调用一个方法来过滤列表
- 将其转换回原始类型 T 列表。
上面的 1 和 2 工作正常,但我 运行 在第 3 步遇到问题。
这是我的代码:
IEnumerable<IMyInterface> castedArray = originalTypedArray as IEnumerable<IMyInterface>;
if (castedArray != null)
{
var filteredArray = castedArray.Where(r => r.Ids.Contains(MyId)).ToList();
IEnumerable<T> castedBackToOriginalTypeArray = filteredArray as IEnumerable<T>;
if (castedBackToOriginalTypeArray == null)
{
current = new List<T>();
}
else
{
current = castedBackArray;
}
// I need to cast back, because only my Type T has the .Id property
List<int> ids = current.Select(r => r.Id).ToList();
}
问题出在这一行:
IEnumerable<T> castedBackToOriginalTypeArray = filteredArray as IEnumerable<T>;
这似乎总是 return null(而不是将过滤后的数组强制转换回 IEnumerable。
这里有关于我可能做错了什么以及如何更正将接口数组转换回 T 类型数组的任何建议吗?
这对我有用:
public class A : IA {
}
public interface IA {
}
List<A> l = new List<A> { new A(), new A(), new A() };
IEnumerable<IA> ias = l.Cast<IA>();
IEnumerable<A> aTypes = ias.Cast<A>();
您不需要将其强制转换为 IEnumerable<IMyInterface>
,或者运行时已正确阻止您编写错误代码。
让我们举一个更小的例子:
void SomeMethod<T>(IEnumerable<T> originalTypedArray, int MyId)
where T : class, IMyInterface
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ this is important
{
if (originalTypedArray != null)
{
var filteredArray = originalTypedArray.Where(r => r.Ids.Contains(MyId));
// No need to cast to `IEnumerable<T>` here - we already have ensured covariance
// is valid in our generic type constraint
DoSomethingExpectingIEnumerableOfIMyInterface(filteredArray);
}
}
void DoSomethingExpectingIEnumerableOfIMyInterface(IEnumerable<IMyInterface> src)
{
foreach (var thing in src)
{
}
}
但是,如果您没有将集合获取为IEnumerable<T>
,那么运行时正确地使转换失败:
void SomeMethod<T>(IEnumerable<IMyInterface> originalTypedArray, int MyId)
我们可以给它一堆 IEnumerable<Apple>
假设 Apple : IMyInterface
。然后您尝试将其转换为 IEnumerable<T>
,其中 T = Banana
和繁荣,代码损坏。
在 C# 中,我想获取类型为 "T" 的数组,我知道 "T" 支持接口 "IMyInterface" 和:
- 将其转换为 "IMyinterface" 的数组
- 对该数组调用一个方法来过滤列表
- 将其转换回原始类型 T 列表。
上面的 1 和 2 工作正常,但我 运行 在第 3 步遇到问题。
这是我的代码:
IEnumerable<IMyInterface> castedArray = originalTypedArray as IEnumerable<IMyInterface>;
if (castedArray != null)
{
var filteredArray = castedArray.Where(r => r.Ids.Contains(MyId)).ToList();
IEnumerable<T> castedBackToOriginalTypeArray = filteredArray as IEnumerable<T>;
if (castedBackToOriginalTypeArray == null)
{
current = new List<T>();
}
else
{
current = castedBackArray;
}
// I need to cast back, because only my Type T has the .Id property
List<int> ids = current.Select(r => r.Id).ToList();
}
问题出在这一行:
IEnumerable<T> castedBackToOriginalTypeArray = filteredArray as IEnumerable<T>;
这似乎总是 return null(而不是将过滤后的数组强制转换回 IEnumerable
这里有关于我可能做错了什么以及如何更正将接口数组转换回 T 类型数组的任何建议吗?
这对我有用:
public class A : IA {
}
public interface IA {
}
List<A> l = new List<A> { new A(), new A(), new A() };
IEnumerable<IA> ias = l.Cast<IA>();
IEnumerable<A> aTypes = ias.Cast<A>();
您不需要将其强制转换为 IEnumerable<IMyInterface>
,或者运行时已正确阻止您编写错误代码。
让我们举一个更小的例子:
void SomeMethod<T>(IEnumerable<T> originalTypedArray, int MyId)
where T : class, IMyInterface
// ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ this is important
{
if (originalTypedArray != null)
{
var filteredArray = originalTypedArray.Where(r => r.Ids.Contains(MyId));
// No need to cast to `IEnumerable<T>` here - we already have ensured covariance
// is valid in our generic type constraint
DoSomethingExpectingIEnumerableOfIMyInterface(filteredArray);
}
}
void DoSomethingExpectingIEnumerableOfIMyInterface(IEnumerable<IMyInterface> src)
{
foreach (var thing in src)
{
}
}
但是,如果您没有将集合获取为IEnumerable<T>
,那么运行时正确地使转换失败:
void SomeMethod<T>(IEnumerable<IMyInterface> originalTypedArray, int MyId)
我们可以给它一堆 IEnumerable<Apple>
假设 Apple : IMyInterface
。然后您尝试将其转换为 IEnumerable<T>
,其中 T = Banana
和繁荣,代码损坏。