Ruby 为什么=~运算符有时只有副作用?
我注意到Ruby/Oniguruma中的一个副作用,它只出现在4个看似等价的语句中的1个语句中。为什么变量Ruby 为什么=~运算符有时只有副作用?,ruby,regex,pattern-matching,irb,oniguruma,Ruby,Regex,Pattern Matching,Irb,Oniguruma,我注意到Ruby/Oniguruma中的一个副作用,它只出现在4个看似等价的语句中的1个语句中。为什么变量day在009中定义,而不是在003、005或007中定义 irb(main):001:0> r = /(?<day>\d\d):(?<mon>\d\d)/ => /(?<day>\d\d):(?<mon>\d\d)/ irb(main):002:0> r =~ "24:12" => 0 irb(main):003:0
day
在009
中定义,而不是在003
、005
或007
中定义
irb(main):001:0> r = /(?<day>\d\d):(?<mon>\d\d)/
=> /(?<day>\d\d):(?<mon>\d\d)/
irb(main):002:0> r =~ "24:12"
=> 0
irb(main):003:0> day
NameError: undefined local variable or method `day'
irb(main):004:0> "24:12" =~ r
=> 0
irb(main):005:0> day
NameError: undefined local variable or method `day'
irb(main):006:0> "24:12" =~ /(?<day>\d\d):(?<mon>\d\d)/
=> 0
irb(main):007:0> day
NameError: undefined local variable or method `day'
irb(main):008:0> /(?<day>\d\d):(?<mon>\d\d)/ =~ "24:12"
=> 0
irb(main):009:0> day
=> "24"
irb(main):001:0>r=/(?\d\d):(?\d\d)/
=>/(?\d\d):(?\d\d)/
irb(主):002:0>r=~“24:12”
=> 0
irb(主要):003:0>天
NameError:未定义的局部变量或方法“day”
irb(主):004:0>“24:12”=~r
=> 0
irb(主要):005:0>天
NameError:未定义的局部变量或方法“day”
irb(主):006:0>“24:12”=~/(?\d\d):(?\d\d)/
=> 0
irb(主要):007:0>天
NameError:未定义的局部变量或方法“day”
irb(main):008:0>/(?\d\d):(?\d\d)/=“24:12”
=> 0
irb(主要):009:0>天
=> "24"
注1:四种情况下都是相同的正则表达式和相同的字符串
注2:我已经验证了微软Windows和Ubuntu Linux中的行为。当你调用“24:12”=~r
时,你实际上调用了“24:12”。=~(r)
。因此,只返回匹配开始的位置,如果没有匹配,则返回nil
但是当你调用/(?\d\d):(?\d\d)/=“24:12”
时,你实际上调用了
正如文件所说
If=~与regexp文本一起使用
使用命名捕获,捕获字符串
(或无)分配给本地
由捕获名称命名的变量
那么003
呢:
如果
regexp不是一个文本
re=/(?\w+)\s*=\s*(?\w+)/
re=~“x=y”
p lhs#未定义的局部变量
p rhs#未定义的局部变量
及
如果
regexp位于右侧。“x=y”=~
/(?\w+)\s*=\s*(?\w+)/
P lhs,rhs#未定义的局部变量
我认为003是不受支持的,因为它在Rubyland中是一个成熟的Regexp对象,可能有重写的方法等等。这使得分配的局部变量的范围更加复杂。谢谢纳什。回答得很好。但是你能解释一下问题中的
003
——也就是说,一个已编译的正则表达式(不是正则表达式文本)接收到=
消息,但它不分配局部变量。“已分配捕获的字符串…”,“未发生分配…”?奇怪的语法…@Tim Pietzckerh,你可以做得更好@蒂姆·皮耶茨克:那一段的作者可能会对你的日语说同样的话;-)我刚刚就文档中的错误向ruby做了一个错误报告(评论)。谢谢,James。关于Ruby创建者的意图,我有另一个想法,但你可能是对的,这是一个技术问题。注意:虽然这里不是这样,但在IRb中处理局部变量时应该小心。由于在IRb中对代码求值的方式不同,它们在IRb中的行为可能与在脚本中稍有不同。始终编写脚本进行确认。
re = /(?<lhs>\w+)\s*=\s*(?<rhs>\w+)/
re =~ " x = y "
p lhs # undefined local variable
p rhs # undefined local variable