java - 为什么字符串在许多编程语言中都是不可变的?

标签 java c++ string immutability

Possible Duplicate:
Why can't strings be mutable in Java and .NET?
Why .NET String is immutable?

为此选择了多种语言,例如 C#、Java 和 Python。如果它的目的是节省内存或提高比较等操作的效率,那么它对串联和其他修改操作有什么影响?

最佳答案

不可变类型通常是一件好事:

  • 它们更适合并发(您不需要锁定无法更改的内容!)
  • 它们减少了错误:可变对象很容易在您没有预料到的情况下被更改,这可能会引入各种奇怪的错误(“远距离操作”)
  • 它们可以安全地共享(即对同一对象的多个引用),这可以减少内存消耗并提高缓存利用率。
  • 如果您必须获取可变对象的防御性拷贝,则共享还可以使复制操作成为非常便宜的 O(1) 操作,而原本的操作成本是 O(n)。这是一件大事,因为复制是一种非常常见的操作(例如,每当您想传递参数时......)

因此,使字符串不可变是一个非常合理的语言设计选择。

有些语言(特别是函数式语言,如 Haskell 和 Clojure)甚至更进一步,使几乎所有内容都是不可变的。这个enlightening video如果您对不变性的好处感兴趣,那么非常值得一看。

不可变类型有一些小缺点:

  • 创建更改的字符串(例如连接)的操作成本更高,因为您需要构造新对象。连接两个不可变字符串的成本通常为 O(n+m),但如果您使用基于树的字符串数据结构(如 Rope),成本可以低至 O(log (m+n))。 。另外,您始终可以使用特殊工具,例如 Java 的 StringBuilder如果您确实需要有效地连接字符串。
  • 对大字符串的微小更改可能会导致需要构造大字符串的全新拷贝,这显然会增加内存消耗。但请注意,这在垃圾收集语言中通常不是一个大问题,因为如果您不保留对旧拷贝的引用,它很快就会被垃圾收集。

总体而言,不变性的优点远远超过了小缺点。即使您只对性能感兴趣,复制的并发优势和廉价性通常也会使不可变字符串比具有锁定和防御性复制的可变字符串具有更高的性能。

关于java - 为什么字符串在许多编程语言中都是不可变的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19116097/

相关文章:

C#,使用字符串的属性

python - python 中只有部分 unicode 被替换。不明白为什么

java - 如何让 IntelliJ IDEA 正确从 Maven 导入 RinSim?

c++ - 用户、错误、异常消息的存储 (c++)

java - 带有 $in 运算符的 mongodb find() 是顺序的还是并行的?

c++ - 使用引用时 vector 的意外行为

c++ - 为什么不能在类范围内推导我的类静态自动函数的类型?

c# - 在 C# 中检查字符串是否有大写字母的最快方法是什么?

本地主机 Java 客户端错误 : MasterNotDiscoveredException[waited for [30s]] 上的 Elasticsearch 2.1.1

java - 如何从 Java 代码编写乐观和悲观锁定