【问题标题】:Get an argument error in ruby blocks在 ruby​​ 块中获取参数错误
【发布时间】:2014-10-02 05:52:05
【问题描述】:
module Framework
 class CreateTableDefinition 
   attr_accessor :host, :username, :password
 end 
end

def create_table(table_name)
  obj = Framework::CreateTableDefinition.new
  yield(obj) if block_given?
end

create_table :users do |config|
  config.host :localhost
end

这是我得到的错误

-:13:in `block in <main>': wrong number of arguments (1 for 0) (ArgumentError)
    from -:9:in `create_table'
    from -:12:in `<main>'

如果我将代码更改为

config.host = :localhost

它工作正常。但我想要的是按照上面的描述工作 config.host :localhost

【问题讨论】:

  • 听起来您希望CreateTableDefinition 类有一个host 方法,该方法将其参数分配给@host 本地,听起来对吗?
  • @AndrewPiliser,正确,但我想省略 = 我发现大多数 RoR 代码都会像 config.host :localhost 那样进行分配。见不 =

标签: ruby block yield


【解决方案1】:

你错过了任务:

config.host = :localhost

编辑

如果你想摆脱赋值,你需要在末尾定义不带=的setter方法。这可能会引用很多代码,所以我宁愿使用一些元编程(因为它很有趣!)

class MyConfigClass
  def self.attributes(*args)
    args.each do |attr|
      define_method attr do |value|
        @attributes[attr] = value
      end
    end
  end

  def initialize
    @attributes = {}
  end

  def get(attr)
     @attributes[attr]
  end 
end

class CreateTableDefinition < MyConfigClass
   attributes :host, :username, :password
end

c = CreateTableDefinition.new
c.host :localhost
c.get(:host)   #=> :localhost 

【讨论】:

  • 我知道,但是如何使用 config.host :localhost?我正在学习 ruby​​,并注意到大多数 RoR 块都以这种方式进行分配
  • @MZON - 我不会说大多数,rails 配置使用标准分配。我会在一秒钟内用如何做到这一点来更新问题。
【解决方案2】:

尝试手动创建一种方法,而不是使用attr_accessor 快捷方式。

class CreateTableDefinition 
  attr_accessor :username, :password

  def host(sym)
    @host = sym
  end

  def get_host
    @host
  end
end

如果您不喜欢为每个属性编写这些方法的想法,请考虑编写自己的帮助程序,例如 attr_rails_like,并将其混合到 Class 对象中。 This 文章可能会有所帮助。

【讨论】:

    猜你喜欢
    • 2019-02-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-06-27
    • 2021-11-04
    • 2021-06-01
    • 2021-02-01
    相关资源
    最近更新 更多