在Ruby中何时使用括号和块比较困惑

在Ruby中何时使用括号和块比较困惑,ruby,Ruby,表面上,, Ruby似乎与Java、Php、C等其他面向对象的语言非常相似 但是,当我们开始撞到街区时,事情就变得有点奇怪了 例如,这是有效的 (0...8).max() => 7 但事实并非如此 (0...8).map(puts "hello world") hello world ArgumentError: wrong number of arguments(1 for 0) 很明显,map方法不接受参数,而是接受块,所以用{}传递replacement可以修复错误 (0..

表面上,, Ruby似乎与Java、Php、C等其他面向对象的语言非常相似

但是,当我们开始撞到街区时,事情就变得有点奇怪了

例如,这是有效的

(0...8).max()
 => 7 
但事实并非如此

(0...8).map(puts "hello world")
hello world
ArgumentError: wrong number of arguments(1 for 0)
很明显,map方法不接受参数,而是接受块,所以用{}传递replacement可以修复错误

(0...8).map{puts "hello world"}
hello world
hello world
hello world
hello world
hello world
hello world
hello world
hello world
 => [nil, nil, nil, nil, nil, nil, nil, nil] 
然后,有些方法应该同时使用块和参数

8.downto(1){puts "hello world"}
hello world
hello world
hello world
hello world
hello world
hello world
hello world
hello world
 => 8 
我的问题是在给定的方法上是否应该使用,{}或两者都使用的问题。根据什么决定

它是基于每个方法固定的吗?我只是想记住该方法采用的是块还是参数? 或者,如果该方法采用块{}或参数,是否有任何其他逻辑推理作为决定它的基础?
请帮助我理解

它应该记录在方法的API中


如果有一个方法接受一个参数,那么块通常是可选的-在这种情况下,它用于优化方法的工作方式-例如Hash.new,它可以接受一个参数、默认哈希值和一个块,用于在键值初始化期间执行智能操作。但是大多数需要块的方法不接受参数,例如Arrayselect或Arraymap。

方法调用后的括号实际上是可选的

0…8.map{puts hello world}相当于0…8.map{puts hello world}

所以你不会真的替换它们

块的验收完全取决于方法,它们可以在方法声明中指定:

def method(param, &block)
  block.call
end
这将允许块作为变量从方法中访问,并通过block.call调用

它们也可以通过使用yield关键字隐式使用:


因此,您必须参考API文档以确定哪些内容被接受或不被接受。

您使用括号将参数传递给函数。这始终是一个以逗号分隔的对象列表。它们可能是函数的结果,但不一定非要如此。它们产生的函数将始终只被精确调用一次

例如:

x = Array.new
=> []
x.push(2)
=> [2]
x.push(7.modulo(4))
=> [2,3]
(0..8).each{ |number| 
  if number.odd?
    puts "#{number} is odd"
  end
}
=> 1 is odd
=> 3 is odd
=> 5 is odd
=> 7 is odd
=> => 0..8
使用块将函数行为传递给方法。这些函数通常打算用许多不同的参数或一定的次数来调用。puts hello world是一个打印某些内容的函数,但只返回nil。因此,您几乎不会尝试将其用作函数的参数,因为您会将nil传递给该函数,但通常会将其作为块传递给函数,以便可以多次调用它

在大多数情况下,您希望将传递给函数的块使用参数,这样每次调用它时,它实际上都会执行不同的操作

例如:

x = Array.new
=> []
x.push(2)
=> [2]
x.push(7.modulo(4))
=> [2,3]
(0..8).each{ |number| 
  if number.odd?
    puts "#{number} is odd"
  end
}
=> 1 is odd
=> 3 is odd
=> 5 is odd
=> 7 is odd
=> => 0..8