2014-09-19 56 views
0

我厌倦了使用if循环,因为.each函数在应用于一个对象时不起作用。Ruby替代.each()与一个项目一起工作

例如:

@groups = ... 
users = User.find(params[:selected_users]) 

if params[:selected_users].count == 1 # case with one object 
    users.some_method() 
else       # case with multiple objects 
    users.each do |user| 
    user.some_method() 
    end 
end 

有没有会做同样的.each当应用到一个对象,它只会返回对象的功能?

+0

if params [:selected_users] .count == 1#case with one object users.some_method() else#case with multiple objects users.each do | user | user.some_method() end end在这里我们有不同的方法吗?例如some_method()或两者相同 – Sanket 2014-09-19 09:27:38

+4

您的代码有问题。如果您将一个(ids)数组传递给['find'](http://api.rubyonrails.org/classes/ActiveRecord/FinderMethods.html#method-i-find),它将返回一个数组,即使该数组只包含一个id:'User.find([1])#=> [#]'。 – Stefan 2014-09-19 09:32:06

+0

@Sanket是的方法是相同的。 你是对的@Stefan,所以我认为写'users = User.find([params [:selected_users]])'可能是最好的解决方案。 – user284130 2014-09-19 11:10:45

回答

1

,你可以这样:

users = Array.wrap(User.find(params[:selected_users])) 
#users is now always an array 
users.each do |user| 
    # do stuff 
end 

Array.wrap处理一些边缘情况优于例如:

x = {a: "b", c: "d"} 

Array(x) 
# => [[:a, "b"], [:c, "d"]] 

Array.wrap(x) 
# =>[{:a=>"b", :c=>"d"}] 
+1

在'find()'方法中添加额外的括号作为@Stefan建议的更聪明,在其他情况下(例如使用范围时),我将使用您的解决方案。 – user284130 2014-09-19 11:20:24

1

你可以这样写:

Array(users).each do |user| 
    user.some_method 
end 

一些例子是什么呢Array()。如果调用一个参数:

> Array(:foo) 
# => [:foo] 

如果所谓的东西,已经是一个数组:

> Array([:foo]) 
# => [:foo] 
0

您可以使用find_each

User.where(id: params[:selected_users]).find_each do |user| 
    user.some_method 
end 

这是行不通的,如果你想与他们做一些后记虽然。我刚刚注意到您的@groups,如果您之后需要在视图中使用它们,那么您需要其他建议之一。

0

,你能做些什么来一个数组arreach

arr.each{|e| ...} #=> arr 

你可以做一个单一的对象objtap

obj.tap{|e| ...} #=> obj 
0

我同意所有的答案打算解决的问题链接到ActiveRecord。

但是,另一个选项可能是将每个对象扩展到每个对象,因此重复对象只发生在对象本身上。

例:

class Object 
    def each 
    if block_given? 
    [self].each { |e| yield(e) } 
    end 
end 

我不是核心Ruby的一个出口,所以我不知道可能是什么副作用,但它似乎工作....

1.each{|i|puts i} 
=> [1] 
[1,2,3].each{|i|puts i} 
=> [1, 2, 3] 
相关问题