我想将字符串转换为通用类型,例如int
或date
或long
基于通用返回类型。
基本上,像Parse<T>(String)
这样的函数返回type的项目T
。
例如,如果传递了一个int函数应该在int.parse
内部执行。
Answers:
根据您的示例,您可以执行以下操作:
int i = (int)Convert.ChangeType("123", typeof(int));
DateTime dt = (DateTime)Convert.ChangeType("2009/12/12", typeof(DateTime));
为了满足您的“通用返回类型”要求,您可以编写自己的扩展方法:
public static T ChangeType<T>(this object obj)
{
return (T)Convert.ChangeType(obj, typeof(T));
}
这将允许您执行以下操作:
int i = "123".ChangeType<int>();
IConvertable
是否也应该限制T
,即T ChangeType<T>(this object obj) where T : IConvertable
?
obj
必须是IConvertible
,但是无法在编译时指定它。
好吧,看来我来不及回答这个问题了。但是这是我的实现:
基本上,我为Object类创建了一个Extension方法。它处理所有类型,即可为空,类和结构。
public static T ConvertTo<T>(this object value)
{
T returnValue;
if (value is T variable)
returnValue = variable;
else
try
{
//Handling Nullable types i.e, int?, double?, bool? .. etc
if (Nullable.GetUnderlyingType(typeof(T)) != null)
{
TypeConverter conv = TypeDescriptor.GetConverter(typeof(T));
returnValue = (T) conv.ConvertFrom(value);
}
else
{
returnValue = (T) Convert.ChangeType(value, typeof(T));
}
}
catch (Exception)
{
returnValue = default(T);
}
return returnValue;
}
TypeDescriptor
为可空类型和Convert.ChangeType
不可空类型使用特定的原因?整个try
块只能缩减为TypeConverter
两行代码,并且对可空和不可空都适用。
清洁Pranay答案的版本
public static T ConvertTo<T>(this object value)
{
if (value is T variable) return variable;
try
{
//Handling Nullable types i.e, int?, double?, bool? .. etc
if (Nullable.GetUnderlyingType(typeof(T)) != null)
{
return (T)TypeDescriptor.GetConverter(typeof(T)).ConvertFrom(value);
}
return (T)Convert.ChangeType(value, typeof(T));
}
catch (Exception)
{
return default(T);
}
}
.NET中有两种约定可以将一种类型的对象转换为另一种类型。
但是这些方法比通常的要慢得多 T.Parse(string)
,导致装箱,并且每次您要转换单个值时都涉及大量分配。
对于ValueString,我选择使用反射找到合适的类型的静态解析方法,构建一个调用它的lambda表达式,并缓存已编译的委托以供将来使用(请参阅此答案以获取示例)。
如果类型没有合适的解析方法,它也会退回到我上面提到的方式(请参阅自述文件中的性能部分)。
var v = new ValueString("15"); // struct
var i = v.As<int>(); // Calls int.Parse.