代码之家  ›  专栏  ›  技术社区  ›  Seth Tisue

为什么Matz选择在Ruby中使字符串在默认情况下可变?

  •  43
  • Seth Tisue  · 技术社区  · 16 年前

    与这个问题相反: Why can't strings be mutable in Java and .NET?

    在Ruby中做出这样的选择仅仅是因为操作(appends等)对可变字符串是有效的,还是有其他原因?

    (如果仅仅是效率的话,那就显得很奇怪了,因为Ruby的设计似乎没有高度重视方便高效的实现。)

    2 回复  |  直到 9 年前
        1
  •  32
  •   rjh    16 年前

    正如您所注意到的,这与Ruby的设计是一致的。不可变字符串比可变字符串效率更高—由于字符串被重复使用,因此复制更少—但这会使程序员的工作更加困难。将字符串视为可变的是很直观的—您可以将它们连接在一起。为了解决这个问题,Java默默地翻译串联(通过 + )使用StringBuffer对象时使用两个字符串,我相信还有其他类似的黑客。Ruby选择在默认情况下使字符串可变,而牺牲了性能。

    Ruby还有很多破坏性的方法,比如 String#upcase! 依赖于字符串是可变的。

    另一个可能的原因是Ruby的灵感来自Perl,而Perl恰好使用可变字符串。

    Ruby有符号和冻结字符串,它们都是不可变的。作为额外的好处,每个可能的字符串值的符号都保证是唯一的。

        2
  •  5
  •   Kelvin    13 年前

    这是我的意见,不是马茨的。为了回答这个问题,当我说一种语言有“不可变的字符串”时,这意味着

    1. “不可变字符串”设计将字符串视为两者 (例如,作为哈希键和其他VM内部使用)和 数据存储结构 . 其思想是标识符是可变的是危险的。对我来说,这听起来像是违反了单一责任。在Ruby中,我们有用于标识符的符号,因此字符串可以自由地充当数据存储。Ruby确实允许字符串作为散列键,但我认为程序员很少将字符串存储到变量中,将其用作散列键,然后修改字符串。在程序员的心目中,字符串的两种用法是分开的。通常情况下,用作哈希键的字符串是文本字符串,因此几乎不可能发生突变。使用字符串作为哈希键与使用两个字符串的数组作为哈希键没有太大区别。只要你的大脑能很好地掌握你用什么作为钥匙,那就没有问题了。

    2. 从认知简单性的角度来看,使用字符串作为数据存储非常有用。只需考虑java及其 StringBuffer . 它是一个额外的数据结构(在一个已经很大而且通常不直观的标准库中),如果您试图执行字符串操作(比如在另一个字符串的某个索引处插入一个字符串),则必须对其进行管理。因此,一方面,Java认识到需要执行这些类型的操作,但是由于不可变的字符串暴露给程序员,他们必须引入另一种结构,这样操作仍然是可能的,而不需要我们重新发明轮子。这给程序员带来了额外的认知负荷。

    3. insert new_with_inserted 或者像这样奇怪的事情。在日常使用中,“插入”意味着你改变了插入的东西的内容(例如,将信封插入邮箱会改变邮箱的内容)。这又提出了一个问题:“为什么我不能更改我的数据存储?”

    推荐文章