如何解决Kotlin-字符串插值$ vs使用加号+ =连接
问题很简单:
这两个版本(都初始化了var name: String
和val someInt: Int
)之间有什么区别?
name += " $someInt"
name = "$name $someInt"
我也读过www.example.com/id-2/home,所以第二个代码应该比第一个(使用串联)更优先?
解决方法
找出差异的最好方法是查看生成的字节码(我将使用Kotlin 1.4.10)。
为name += " $someInt"
生成的字节码:
ALOAD 0
NEW java/lang/StringBuilder
DUP
INVOKESPECIAL java/lang/StringBuilder.<init> ()V
SWAP
INVOKEVIRTUAL java/lang/StringBuilder.append (Ljava/lang/String;)Ljava/lang/StringBuilder;
BIPUSH 32
INVOKEVIRTUAL java/lang/StringBuilder.append (C)Ljava/lang/StringBuilder;
ILOAD 1
INVOKEVIRTUAL java/lang/StringBuilder.append (I)Ljava/lang/StringBuilder;
INVOKEVIRTUAL java/lang/StringBuilder.toString ()Ljava/lang/String;
ASTORE 0
为name = "$name $someInt"
生成的字节码:
NEW java/lang/StringBuilder
DUP
INVOKESPECIAL java/lang/StringBuilder.<init> ()V
ALOAD 0
INVOKEVIRTUAL java/lang/StringBuilder.append (Ljava/lang/String;)Ljava/lang/StringBuilder;
BIPUSH 32
INVOKEVIRTUAL java/lang/StringBuilder.append (C)Ljava/lang/StringBuilder;
ILOAD 1
INVOKEVIRTUAL java/lang/StringBuilder.append (I)Ljava/lang/StringBuilder;
INVOKEVIRTUAL java/lang/StringBuilder.toString ()Ljava/lang/String;
ASTORE 0
结果几乎相同,但是在第一种情况下,有一个额外的SWAP
操作,导致第一个append
操作的参数过早加载到堆栈中(在StringBuilder
被加载之前创建,现在需要交换它们。
TL; DR
结果是:
-
两种情况下都会创建
-
StringBuilder
- 两种情况下都有3个附加项(
name
,空格和someInt
) - 第二个更有效。
语义是等效的,第二种可能效率更高,但并非完全出于您给出的原因:这是只有一个串联而不是两个。 (第一个首先生成" " + someInt
,然后生成name + (" " + someInt)
。)
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。