将字符串强制转换为 IEnumerable
本文关键字:IEnumerable object 转换 字符串 | 更新日期: 2023-09-27 18:27:40
我有propertyValue
,这是一个传递给我的函数的对象。
我可以假设这是某种IEnumerable
,但是由于接口合约,我必须将其作为object
而不是直接作为IEnumerable
接受。
当我尝试将我的值转换为IEnumerable<object>
,以便我可以得到长度时,我得到了一个InvalidCastException
。
var length = ((IEnumerable<object>) propertyValue).Cast<object>().Count();
我得到以下异常:
System.InvalidCastException: 无法强制转换类型的对象 要键入的"系统字符串" 'System.Collections.Generic.IEnumerable'1[System.Object]'.
IEnumerable<T>
接口是协变的,但协方差不适用于值类型。将值类型强制转换为引用类型会更改表示形式 - 需要对值进行装箱,并返回对装箱值的引用。强制转换引用类型不会更改表示形式 - 它仍然是相同的引用,引用相同的对象。
string
是IEnumerable<char>
,所以不能投射到IEnumerable<object>
。
如其他答案所述,解决方案是转换为非泛型IEnumerable
。
var length = ((IEnumerable) propertyValue).Cast<object>().Count();
我已经通过简单地转换为IEnumerable
而不是转换为IEnumerable<object>
来解决此问题。
var length = ((IEnumerable) propertyValue).Cast<object>().Count();
String 实现 IEnumerable<char>
接口,可以将其强制转换为此接口
var length = ((IEnumerable<char>) propertyValue).Count();
对于未知类型的集合,可以使用自己的扩展方法将其强制转换为 IEnumerable 和下一个枚举值。
static class EnumerableExtensions
{
public static int Count(this IEnumerable source)
{
int res = 0;
foreach (var item in source)
res++;
return res;
}
}
var collection = propertyValue as IEnumerable;
if(collection != null)
{
var length = collection.Count();
}
使用 Cast(( 方法将导致值类型的装箱,并且对于大型集合可能会有性能问题。
以下代码实际上应该可以满足您的需求
var length = (propertyValue as IEnumerable<object>).Count();