Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/ruby-on-rails/61.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ruby on rails 在Ruby中,我可以在initialize方法中自动填充实例变量吗?_Ruby On Rails_Ruby - Fatal编程技术网

Ruby on rails 在Ruby中,我可以在initialize方法中自动填充实例变量吗?

Ruby on rails 在Ruby中,我可以在initialize方法中自动填充实例变量吗?,ruby-on-rails,ruby,Ruby On Rails,Ruby,在Ruby中,我可以在initialize方法中自动填充实例变量吗 例如,如果我有: class Weekend attr_accessor :start_date, :end_date, :title, :description, :location def initialize(params) # SOMETHING HERE TO AUTO POPULATE INSTANCE VARIABLES WITH APPROPRIATE PARAMS end end 为了

在Ruby中,我可以在initialize方法中自动填充实例变量吗

例如,如果我有:

class Weekend
  attr_accessor :start_date, :end_date, :title, :description, :location

  def initialize(params)
    # SOMETHING HERE TO AUTO POPULATE INSTANCE VARIABLES WITH APPROPRIATE PARAMS
  end

end
为了保持简单:

class Weekend
  attr_accessor :start_date, :end_date, :title, :description, :location

  def initialize(params)
    @start_date = params[:start_date] # I don't really know the structure of params but you have the idea
    @end_date   = params[:end_date]
  end
end
您可以通过元编程来做一些更聪明的事情,但这真的有必要吗?

您可以这样使用:

params.each do |key, value|
  self.instance_variable_set("@#{key}".to_sym, value)
end
我建议

class Weekend
  @@available_attributes = [:start_date, :end_date, :title, :description, :location]
  attr_accessor *@@available_attributes

  def initialize(params)
    params.each do |key,value|
      self.send(:"#{key}=",value) if @@available_attributes.include?(key.to_sym)
    end
  end
end

Ruby有时很简单。看不见有环

class Weekend < Struct.new(:start_date, :end_date, :title, :description, :location)
  # params: Hash with symbols as keys
  def initialize(params)
    # arg splatting to the rescue
    super( * params.values_at( * self.class.members ) )
  end
end
测试:

注意,这实际上并没有设置实例变量。您的类将有不透明的getter和setter。如果您不想公开它们,可以围绕它包装另一个类。下面是一个例子:

# this gives you more control over readers/writers
require 'forwardable'
class Weekend
  MyStruct = ::Struct.new(:start_date, :end_date, :title, :description, :location)
  extend Forwardable
  # only set up readers
  def_delegators :@struct, *MyStruct.members

  # params: Hash with symbols as keys
  def initialize(params)
    # arg splatting to the rescue
    @struct = MyStruct.new( * params.values_at( * MyStruct.members ) )
  end
end

我想你可以简单地说:

Weekend < Struct.new(:start_date, :end_date, :title, :description, :location)

我理解避免不必要的元编程的愿望,但这并不是OP所要求的简洁代码。你必须手动指定每个字段名。我回来回答两年前看到的这个问题,只是为了找到一年前给出我心中答案的人。(但我更喜欢
class Weekend
一个常量
可用的\u属性如何,而不是一个类变量?@BKSpurgeon我不知道它有多常见。如果你打算在团队项目中使用它,我建议询问团队是否接受它。
# this gives you more control over readers/writers
require 'forwardable'
class Weekend
  MyStruct = ::Struct.new(:start_date, :end_date, :title, :description, :location)
  extend Forwardable
  # only set up readers
  def_delegators :@struct, *MyStruct.members

  # params: Hash with symbols as keys
  def initialize(params)
    # arg splatting to the rescue
    @struct = MyStruct.new( * params.values_at( * MyStruct.members ) )
  end
end
Weekend < Struct.new(:start_date, :end_date, :title, :description, :location)
class Weekend
#whatever you need to add here
end