我想知道这段代码的含义,以发现一个可能的错误:
-> a, b, c, d, e, f, g, h, i, j {
l = -> s, t = c {
Math.log(s, t)
}
}
谢谢
答案 0 :(得分:5)
第一部分:-> a, b, c, d, e, f, g, h, i, j { ... }
是lambda或匿名函数的声明。
其中a,b,c ...等是要作为变量传递到块{..}
这与lambda { |a,b,c,...j| ... }
您可以在此处看到类似的示例:
ex1 = -> a,b,c,d {
puts a;
puts b;
puts c;
}
ex1.call('1', '2', '3', '4');
然后在其中返回另一个lambda:
l = {->
s,t = c {Math.log(s,t)
由->
符号表示,并且默认t
参数是外部lambda中先前提供的c
arg。
最后,它从内部lambda的s和t参数调用Math.log。
这是简化版:
ex2 = -> a,b { c = -> d, e = b { puts d; puts e } }
ex2.call(1,2).call(3) # e is optional since it's defaulted to b
# => 3,2
注意:您的代码缺少一些}
。
答案 1 :(得分:4)
说实话,这段代码绝对可怕。得知只有一个错误,我会感到惊讶。
这是一个重写:
weird_log = lambda do |_, _, default_base, _, _, _, _, _, _, _|
lambda do |x, base=default_base|
Math.log(x, base)
end
end
它更具可读性,并且很清楚方法签名是无用的。在原始代码中,10个原始参数中仅使用c
。
a, b, d, e, f, g, h, i, j
未使用,因此可以将其重命名为_
。即使不使用它们,也需要指定它们:
weird_log.call(nil, nil, 10)
#=> ArgumentError: wrong number of arguments (given 3, expected 10)
weird_log.call(nil, nil, 10, nil, nil, nil, nil, nil, nil, nil)
#=> #<Proc:0x00000000031e57c8@(pry):9 (lambda)>
weird_log.call(nil, nil, 10, nil, nil, nil, nil, nil, nil, nil).call(100)
#=> 2.0
weird_log.call(nil, nil, 10, nil, nil, nil, nil, nil, nil, nil).call(100, Math::E)
# => 4.605170185988092
一种不太神秘的方式是:
def my_log(base = Math::E)
->(x) { Math.log(x, base) }
end
可以这样使用:
log10 = my_log(10)
# => #<Proc:0x000000000222d2b8@(irb):2 (lambda)>
log10.call(100)
# => 2.0
natural_log = my_log
#=> #<Proc:0x0000000002243540@(irb):2 (lambda)>
natural_log.call(10)
#=> 2.302585092994046
但是,您最好直接使用Math.log
:
Math.log(100, 10)
# => 2.0
Math.log(10)
# => 2.302585092994046