自动.ToString()?

时间:2010-09-21 10:21:35

标签: c# .net interface tostring

我有一个这样的方法:void m1(string str)并且有一个这样的类:

public class MyClass
{
    public bool b1 { set; get; }

    //and other properties
}

现在为什么以下代码不会导致编译错误?

IClass2 _class2 = new Class2();
MyClass c1 = new MyClass();
_class2.m1("abcdef" + c1);

当我调试它时,我意识到c1.ToString()已传递给m1。为什么会发生这种自动.ToString()?我唯一可以说的是m1已在IClass2界面中定义,并由Class2实现。

2 个答案:

答案 0 :(得分:8)

这遵循围绕字符串连接的C#语言规范的规则。参见C#4规范的第7.8.4节(加法运算符)

  

字符串连接:

string operator +(string x, string y);
string operator +(string x, object y);
string operator +(object x, string y);
     

二进制+运算符的这些重载执行字符串连接。如果字符串连接的操作数是null,则替换空字符串。否则,通过调用从类型对象继承的虚拟ToString方法,将任何非字符串参数转换为其字符串表示形式。如果ToString返回null,则会替换空字符串。

如果您没想到会发生这种情况,请问您对"abcdef" + c1表达式的结果有何看法?

请注意,m1IClass2Class2与此处发生的事情无关 - 它只是真正相关的连接表达式:触发对ToString()的调用的是什么,不管后来发生在那个字符串上的是什么。

答案 1 :(得分:6)

编译器将"abcdef" + c1转换为string.Concat(object,object)来电。这反过来会在每个参数上调用.ToString()并将它们连接起来。这是反射器的代码:

public static string Concat(object arg0, object arg1)
{
   if(arg0 == null) arg0 = Empty;
   if(arg1 == null) arg1 = Empty;

   return (arg0.ToString() + arg1.ToString());
}

请注意,最后一行涉及对string.Concat(string, string)的调用,其中真正的连接发生。