gpt4 book ai didi

ruby - 为什么 Ruby 中的双铲不改变状态?

转载 作者:数据小太阳 更新时间:2023-10-29 06:41:37 24 4
gpt4 key购买 nike

我遇到了导致错误或困惑的奇怪副作用。所以想象一下,这不是一个微不足道的例子,而是一个陷阱的例子。

name = "Zorg"

def say_hello(name)
greeting = "Hi there, " << name << "?"
puts greeting
end

say_hello(name)
puts name

# Hi there, Zorg?
# Zorg

这不会改变名称。姓名仍为Zorg .

但是现在来看一个非常细微的差别。在下一个示例中:

name = "Zorg"

def say_hello(name)
greeting = name << "?"
puts "Hi there, #{greeting}"
end

say_hello(name)
puts name

# Hi there, Zorg?
# Zorg? <-- name has mutated

现在名称是 Zorg? .疯狂的。 greeting = 的细微差别|任务。 Ruby 在内部使用解析(?)或消息传递链接做一些事情?我以为这只会像 name.<<("?") 一样把铲子链起来但我想这不会发生。

这就是为什么我在尝试进行串联时避免使用铲子运算符。我通常尽量避免改变状态,但 Ruby(目前)还没有为此进行优化(还)。也许 Ruby 3 会改变一切。对于关于 Ruby future 的范围蔓延/旁白讨论,我们深表歉意。

我认为这特别奇怪,因为副作用较少的示例(第一个)有两个铲操作符,而副作用较多的示例有较少的铲操作符。

更新你是对的 DigitalRoss,我把它弄得太复杂了。简化示例:

one = "1"
two = "2"
three = "3"
message = one << two << three

现在你认为一切都准备好了? (不要偷看!)如果非要我猜的话,我会说:

one is 123
two is 23
three is 3
message is 123

但我错了两个。二是 2。

最佳答案

如果我们转换您的 a << b << c构造成更像方法的形式并放入一堆隐式括号,行为应该更清晰。重写:

greeting = "Hi there, " << name << "?"

产量:

greeting = ("Hi there, ".<<(name)).<<("?")

String#<< 正在修改东西但是 name永远不会作为 << 的目标/左轴出现, "Hi there ," << name字符串但name没有。如果用变量替换第一个字符串文字:

hi_there = 'Hi there, '
greeting = hi_there << name << '?'
puts hi_there

你会看到 <<已更改 hi_there ;在你的"Hi there, "在这种情况下,此更改是隐藏的,因为您正在修改之后无法查看的内容(字符串文字)。

关于ruby - 为什么 Ruby 中的双铲不改变状态?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40877662/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com