正在努力解决以下问题。我有一个定义数据库表中键名称的属性。使用反射,我初始化具有该属性的属性或字段的值。一切都很好,直到我将我的属性定义为数组:
[ConfigurationKey("TestArray")]
public int[] Array { get; set; }
假设存储在表中的值是逗号分隔的字符串,我使用以下方法来创建一个数组:
return valueString.Split(',').Select(s => Convert.ChangeType(s, memberType.GetElementType())).ToArray();
这确实会创建一个元素数组,但只创建一个对象数组。因此,当我使用 FieldInfo 或 PropertyInfo 设置值时,它会抛出异常"无法将Object[]
分配给Int32[]
"。
有什么想法吗?
鉴于Convert.ChangeType
被声明为返回Object
,我认为这并不特别令人惊讶。 ToArray()
将创建一个与输入序列具有相同元素类型的数组,在这种情况下,Select
将返回一个IEnumerable<object>
。
一种选择是使用反射调用Cast
(然后调用ToArray
)。老实说,将所有内容放入单个泛型方法中可能是最简单的,并通过反射调用它:
public static T[] ParseToArray<T>(string valueString)
{
return valueString.Split(',')
.Select(s => (T) Convert.ChangeType(s, typeof(T))
.ToArray();
}
然后,您需要:
Type t = memberType.GetElementType();
// Use the type declaring ParseToArray here
MethodInfo methodDefinition = typeof(...).GetMethod("ParseToArray");
MethodInfo method = methodDefinition.MakeGenericMethod(t);
object array = method.Invoke(null, new object[] { valueString });