从泛型方法获取值而不提供类型
本文关键字:类型 泛型方法 获取 | 更新日期: 2023-09-27 18:18:41
我试图创建一个类,其中一个属性是通用的,没有类本身是通用的。我发现你做不到;不允许使用通用属性。我在这里挖了一下,我找到了一个通用的属性,我找到了一个工作,很好地为我工作。
随后,我结束了这门课…
[Serializable]
public class ConfigurationItem
{
private readonly Type type;
public string Description { get; set; }
public IDictionary<string, ConfigurationItem> Items { get; private set; }
public string Name { get; set; }
public string Summary { get; set; }
public object Value { get; private set; }
public ConfigurationItem(string name, Type type = null, object value = null)
{
this.Name = name;
this.type = type ?? typeof(string);
this.Value = value;
Items = new Dictionary<string, ConfigurationItem>();
}
public string Export()
{
return JsonConvert.SerializeObject(this);
}
public T GetValue<T>()
{
return (T)Convert.ChangeType(Value, type);
}
}
现在我唯一的问题是,如果我想获得值,正确转换,我必须在调用GetValue()
时提供类型。本能地,我不禁觉得,既然类知道应该返回的类型,那么我应该可以构造一个不需要我提供任何额外信息的GetValue()
方法。
我想不出是怎么回事。
我确实发现线程得到一个通用的方法来推断类型参数从运行时类型,这似乎表明这是可能的,但我了解很少关于反射,不能使任何意义所说的
是否有一种方法构建一个GetType()
方法,不需要我提供泛型类型?你能用我那弱智的大脑能理解的方式解释一下吗?
编辑许多人实际上已经指出,我真的不需要这样做,尽管如此,作为一个学习练习,我遵循了@ShoaibShakeel的建议,看看c# dynamic
类型,并提出了这些额外的方法…
public dynamic GetValue()
{
return typeof(ConfigurationItem)
.GetMethod("GetReturnValue", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance)
.MakeGenericMethod(type)
.Invoke(this, new object[] { });
}
private T GetReturnValue<T>()
{
return (T)Convert.ChangeType(Value, type);
}
我本能地觉得,既然类知道应该返回的类型
虽然Value
对象确实知道它自己的类型,但是这个信息只在运行时可用(一旦有一个具有类型的实际对象)。因此,为了在编译时获得类型信息,您需要提供必要的信息。毕竟,不可能静态地知道那里赋值了什么对象。
GetValue()
能够自动返回类型的对象,您想用它做什么?var x = configurationItem.GetValue();
那么x
应该是什么类型,之后你想用它做什么?你只想打印出来还是怎么的?那么object
就足够了。你想用它计算什么吗?然后,您可能已经要求它是int
或float
或其他类型,因此您将需要一个实际的静态类型-这就是为什么您必须提供该类型信息。
仅仅因为返回类型是object
,并不意味着对象本身丢失了类型信息。分配给object
属性的字符串仍然是字符串,即使您在很久以后检索它。如果你希望得到一个字符串,并且想对它做些什么,那么你当然可以把它强制转换成一个字符串。
No.
编译器不能从它所赋值的变量推断类型,因为它是二义性的,特别是在大型继承树中。
考虑
一行object o = configurationItem.GetValue<int>();
int
可能是您的值的有效转换,但object
不是,因为object
不实现IConvertible
接口(Convert.ChangeType()
所要求的)。
我能够让我的类返回一个值,正确转换,使用反射和动态使用以下添加到我的原始类。
public dynamic GetValue()
{
return typeof(ConfigurationItem)
.GetMethod("GetReturnValue", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance)
.MakeGenericMethod(type)
.Invoke(this, new object[] { });
}
private T GetReturnValue<T>()
{
return (T)Convert.ChangeType(Value, type);
}