隐式转换为字符串 – toString和int +“”

为什么当我使用它:

int a = 1; methodWithParamString(a + ""); 

a被强制转换为String,我不能在整数上使用toString()吗?

 int a = 1; methodWithParamString(a.toString()); 

这不是: a+""作用类似于: a.toString() + ""

不,它的工作方式类似于String.valueOf( a ) + "" ,它反过来表现得像new StringBuilder( String.valueOf( a ) ).append( "" ).toString()

重要的是要知道它完全由编译器完成,换句话说就是它的语法糖。 这就是为什么在循环中将字符串组合在一起并不是一个好主意。 (尽管现代VM可能有一些机制来降低性能开销。)

a被强制转换为String

不会。它被转换为String。 (您无法隐式或显式地将基本类型转换为String。)

此转换的详细信息在JLS- 15.18.1.1中指定。 该规范声明,对于基本类型,转换“就像”您创建了适当的包装类型的实例,然后在其上调用toString() 。 这使得Java编译器可以选择使用其他方法,只要最终结果相同。 (对于引用类型,转换通过调用toString()null转换为"null" ,将其他非String类型转换为String。)

JLS声明通过调用String.concat(...) “然后”执行连接,注意JLS明确允许优化连接序列。 (JLS 15.18.1.2 )

这不是:a +“”的作用类似于:a.toString()+“”?

真正。 它没有。

+在内部超载。 和Java不支持对基元的方法调用。

因为int a – 不是对象,所以它是原始类型。 所以它没有任何方法。 你应该使用拳击:

 Integer objectA = new Integer(a); objectA.toString(); 

toString()Object类中的一个方法,任何从它inheritance的类都将具有该方法,如IntegerString 。 但int是基本类型而不是Object,因此该方法不存在。

int是原始类型,所以它不是一个对象,不能有任何方法。
阅读本文我认为这将有所帮助。 有基元的包装类,例如int Integer 。 您可以为它们调用toString()方法。
实际上String是java中的一个特殊类。 并且您可以对字符串和基元使用+(而不仅仅是)运算符。 我想你会在这里找到你问题的完整答案。

在Java中实现这一点的方式实际上比其他答案似乎更简单。

将字符串连接运算符与String和对象一起使用会导致调用该对象的toString()方法,然后执行字符串连接。

请记住,只要将原语传递给Object有效的上下文,Java就会执行“autoboxing”,将int转换为Integer ,将double转换为Double ,等等。

因此,您可以将其视为自动装箱,然后是toString(),后跟字符串连接。

同时,您应该意识到JLS字符串连接规范允许JVM实现优化自动装箱,只要结果相同,因此您的JVM可以使用StringBuilder,或使用任何其他有效的JVM字节码来创建结果字符串,所以字符串连接运算符的性能往往比自己执行拳击更好。