我正在开发一个项目,我将命令发送到设备。每个命令对象与设备支持的特定命令(由支持dll的API定义)具有一对一的关系。
我有定义命令的XML文件:命名方法名称和参数(按名称,类型和默认值)。
我的应用程序读取XML并创建一个命令对象。我有一个参数字典,其参数名称与值相关联(按类型)。
填充参数字典时,我开始创建一个类型,然后是一个实例,然后更新字典。
{
theType = Type.GetType(paramType);
var newInstance = Activator.CreateInstance(theType, true);
parameterValueMap.Add(paramName, newInstance);
}
这适用于整数等,但不适用于字符串类型,因为它们没有无参数构造函数。
由于可能有其他类型的无参数构造函数,我需要保持解决方案的通用性(不专门处理字符串)。
有人可以帮我解决这个问题吗?有没有办法用参数创建一个类型的实例,而没有参数的实际实例(以及我特定情况下的字符串实例)?
由于 -m
答案 0 :(得分:1)
由于您提到了泛型,default(T)
可能很有用,但对于类/接口,它将是null
。一个方便的邪恶技巧是:
T obj = (T)FormatterServices.GetUninitializedObject(typeof(T));
然而!这是纯粹的邪恶,通常保留用于反序列化/实现库。这不适用于临时使用。
也许最好的方法是让调用者告诉你如何添加一个可选的工厂参数:
void YourMethod<T>(..., Func<T> constructor = null)
然后如果他们想要,调用者可以提供创建实例的技术。所以你有:
T obj = constructor == null ? (T)Activator.CreateInstance(typeof(T))
: constructor();
无论如何:字符串是一个很大的问题。毫无疑问,您需要使用特殊字符串。
答案 1 :(得分:0)
我在代码中使用Activator.CreateInstance(type, ParseKeys(ID).ToArray())
,其中ID
是||
分隔的键/值对列表,ParseKeys()
是
private static IEnumerable<object> ParseKeys(string keyString)
{
IEnumerable<string> keyStrings = keyString.Split(new string[] { "||" }, StringSplitOptions.RemoveEmptyEntries); // Use this construction to enable splitting on multiple characters
List<object> keys = new List<object>();
foreach (var key in keyStrings)
{
var type = Type.GetType(key.Split("|")[0]);
var value = key.Split("|")[1];
var data = Convert.ChangeType(value, type);
keys.Add(data);
}
return keys;
}
显然,你需要能够以某种形式将你的参数表示为一个字符串,而我没有为无参数构造函数测试它,但它对于整数和字符串都可以正常工作。