繁体   English   中英

通过反射调用“ToString”方法

[英]Invoke “ToString” method by reflection

我正在尝试按如下方式检索 MethodInfo“ToString”:

MethodInfo method = MyType.GetMethod("ToString", 
                                     BindingFlags.Public | BindingFlags.Instance);

抛出异常“找到歧义匹配”。

您的类型包含多个ToString()重载,而GetMethod不知道您想要哪一个。

使用以下语法指定您想要不带任何参数的重载:

MethodInfo method = myType.GetMethod("ToString", Type.EmptyTypes); 

注意:由于ToString()是在System.Object上定义的,你不需要反射来在未知类型的对象上调用它:

object myObject = ...;
string s = myObject.ToString(); // works

ToString()System.Object的成员,因此它是极少数不需要反射的方法之一,当您在未知类型上调用它时。

例外情况是 Tostring 的重载(即int.ToString(string format)但要调用其中之一,您必须知道您要查找的是哪一个。

而这些重叠会导致您看到的错误。 你必须是具体的。

可能有不止一种ToString()方法。 例如double有四个变体( virtual object.ToString()的覆盖加上三个变体)

尝试

var variants = MyType.GetMethods(BindingFlags.Public | BindingFlags.Instance)
               .Where(p => p.Name == "ToString");

它将返回ToString所有变体

或者,如果您知道“您的” ToString的参数

var toString = MyType.GetMethod("ToString", 
               BindingFlags.Public | BindingFlags.Instance, 
               null, arrayOfParametersType, null);

您需要指定您想要没有参数的那个:

var method = MyType.GetMethod("ToString", 
                              new Type[0]);

BindingFlags.Public | BindingFlags.Instance BindingFlags.Public | BindingFlags.Instance为默认值,无需指定。

MethodInfo method = typeof(MyType).GetMethod("ToString", BindingFlags.Public | BindingFlags.Instance);

这实际上对我有用...

您可能在 ToString 上有一个重载。 由于您可以拥有多个公开的 ToString 方法(重载),因此该行可以返回多个 ToString 方法。

你必须使用类似的东西:
GetMethod(字符串名称,类型 [] 类型)

其中 Type[] 包含您正在搜索的方法的类型数组(在您的情况下没有)

(感谢评论,也从中学到了一些东西:)

ToString可以重载。 在许多类型上都是如此。

首先,您应该检查您要调用的ToString是被覆盖的IFormattable.ToString(string format, IFormatProvider formatProvider)) object.ToString()还是IFormattable.ToString(string format, IFormatProvider formatProvider)) ,因为在这些情况下您可以简单地避免反射。

您可以使用采用Type[] types参数的GetMethod重载来选择所需的ToString重载。

例如,您可以使用GetMethod("ToString",new Type[]{})来获取无参数的ToString()

检查是否要覆盖ToString()是否真的使用了override关键字:

class MyType
{
     public override string ToString()
     {
         return "Whatever";
     }
 }

否则,您将隐藏 object.ToString() 版本而不是真正覆盖。

在这样的场景中,当您知道该方法存在时(可能有许多重载使问题复杂化),使用为您完成繁重工作的反射帮助程序库会很有帮助。

例如,Fasterflect 允许您简单地执行以下操作,以便使用给定提供的参数的“最佳可用匹配”调用方法(在下面的示例中,可选参数 42 表示您在调用方法时要使用的某个值):

var obj = ...
var result = obj.TryCallMethodWithValues( "ToString", 42 );

根据我的经验,使用经过良好测试的库而不是手动编码(在本例中为反射)会很快得到回报。

免责声明:我是 Fasterflect 项目的贡献者。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM