将数组操作操作放在Ruby中

时间:2013-10-22 22:15:46

标签: ruby refactoring

我想按特定顺序对数组执行多项操作。每个行为单位都有自己的方法,我有类似的东西:

def build_array_of_cool_employees
  employees = fetch_all_employees
  employees = remove_strange_employees_from employees
  employees = add_ideal_employee_to employees
  employees = sort_by_awesomeness employees
end

我想知道是否有更好的方法。我觉得我错过了一些可以使我的代码更好的功能。我呢?

4 个答案:

答案 0 :(得分:1)

您可以使用可链式方法创建单独的类。像这样:

class EmployeeBuilder
  attr_reader :employees

  def initialize
    @employees = []
  end

  def fetch_all
    @employees.push(:qux, :baz, :bar)
    self
  end

  def remove_strange
    @employees.delete(:qux)
    self
  end

  def add_ideal
    @employees.push(:foo)
    self
  end

  def sort
    @employees.reverse!
    self
  end
end

并称之为:

def build_array_of_cool_employees
  builder = EmployeeBuilder.new
  builder.fetch_all.remove_strange.add_ideal.sort.employees
end

build_array_of_cool_employees
#=> [:foo, :bar, :baz]

答案 1 :(得分:1)

在您的情况下,您应该使用方法链接。如果您不想污染Array类,可以继承Array

class Employees < Array
  def self.cool
    fetch_all
    .remove_strange
    .add_ideal
    .sort_by_awesomeness
  end
  def self.fetch_all
    new(...)
  end
  def remove_strange
    ...
    self
  end
  def add_ideal
    ...
    self
  end
  def sort_by_awesomeness
    ...
    self
  end
end

Employees.cool # => ...

答案 2 :(得分:0)

这个可能会读取得更好,具体取决于你对方法链的感觉,但需要array作为扩展,然后你可以直接在数组上调用自定义方法觉得合适。更好的是拥有员工列表对象然后操纵它,但这个想法是相似的。

class Array
    def sort_by_awesomeness
        #your sort
    end

    def  add_ideal_employee(cool_employee)
        self.push(cool_employee)
    end 
    def remove_strange_employees(uncool_employees)
        uncool_employees.each do |uncool_employee|
            self.delete(uncool_employee)
        end 
        # return self here to continue the method chaining
        return self
    end
end

def build_array_of_cool_employees
  employees = fetch_all_employees.add_ideal_employee(cool_employee).remove_strange_employees(uncool_employees).sort_by_awesomeness
end

答案 3 :(得分:0)

这取决于您的方法的实现方式。如果他们修改了原始数组,你可以这样做:

fetch_all_employees.tap do |employees|
  remove_strange_employees_from(employees)
  add_ideal_employee_to(employees)
  sort_by_awesomeness(employees)
end

请注意,像delete_ifpush这样的方法会修改原始数组,因此如果您在方法的实现中使用它们,它应该可以正常工作。