Ruby语法糖有“规则”吗?
我正在学习Ruby的基础知识(刚刚开始),我遇到了Hash.[]
方法 。 它被引入
a = ["foo", 1, "bar", 2] => ["foo", 1, "bar", 2] Hash[*a] => {"foo"=>1, "bar"=>2}
经过一番思考,我发现Hash[*a]
等同于Hash.[](*a)
或Hash.[] *a
。 我的问题是为什么会这样。 是什么让你把*a
放在方括号内,是否有某种规则可以使用“it”的地方和时间?
编辑:我的措辞似乎引起了一些混乱。 我不是在询问arrays扩展。 我明白了。 我的问题基本上是:如果[]
是一个方法名称,为什么可以在括号内放置参数? 看起来差不多 – 但不完全 – 就像说如果你有一个方法Foo.dood
,并且你想把字符串"hey"
传给它,那么你可以写Foo.do"hey"od
。
ruby允许您以特殊方式调用几种方法。 这些是你提到的[]
, +
, -
, ==
和其他人提到的一样。 另一个重要的例子是formssomething=(value)
,可以使用object.something = value
调用,并允许您创建访问器。
编辑:
有趣的事实1:如果你定义一个+
方法,你得+=
免费。
有趣的事实2:如果你定义一个<=>
你得到所有的比较方法,礼貌的可比较
Hash["a", "b", "c", "d"]
等同于Hash.[]("a", "b", "c", "d")
。 Ruby中的几乎所有东西都是方法调用。 5 + 5
相当于5.+(5)
。
给定a = ["a", "b", "c", "d"]
Hash[*a]
等同于Hash["a", "b", "c", "d"]
,相当于Hash.[]("a", "b", "c", "d")
。 类似地, foo(*a)
等同于foo("a", "b", "c", "d")
这称为爆炸运算符,并允许将数组发送到方法并使数组中的每个项目count作为方法的一个参数,而不是将数组作为第一个参数发送到方法。
要专门回答您的更新,没有什么特别的东西可以让你把*a
放在括号内。 括号只是正常方法调用的糖。 这里唯一的“特殊”是你可以向任何方法发送*a
。
我认为Ruby的语法是在YARV Ruby的parse.y中定义的。
*
方法告诉ruby不要将数组作为数组,而是使用’expanded’数组。
例:
def test(*argv) p argv end a = [1,2,3] test(a) #-> [[1, 2, 3]] test(*a) #-> [1, 2, 3]
使用test(a)
,数组a是唯一的参数。
使用test(*a)
a用作参数列表。
在你的情况下
a = ["foo", 1, "bar", 2] Hash[*a]
类似于
Hash["foo", 1, "bar", 2]
Hash[*a]
会
Hash[["foo", 1, "bar", 2]]