如何“以编程方式"\“以迭代方式"设置每个类对象属性都有一个值? [英] How to set "programmatically"\"iteratively" each class object attribute to a value?

查看:26
本文介绍了如何“以编程方式"\“以迭代方式"设置每个类对象属性都有一个值?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用 Ruby on Rails 3.0.9 和 RSpec 2.我试图通过以下方式重构一些规范文件(为了用更少的代码进行测试,类似的类对象属性值):

<预><代码>[:attribute_a,:attribute_b,:attribute_c].each 做 |attr|在做之前# 这里我想设置当前"'attr' 相关的# 类对象实例 'attribute_<字母 >'(阅读下面的# 更多信息)每次调用迭代器时(注意:所有# 以下属性不是 attr_accesible - 因此# 我使用'user.attribute_<字母 >'在之前做"# 陈述)## # 迭代 1# user.attribute_a = 'a_value'# # 'user.attribute_b' 没有变化# # 'user.attribute_c' 没有变化## # 迭代 2# # 'user.attribute_a' 没有变化# user.attribute_b = 'a_value'# # 'user.attribute_c' 没有变化## # 迭代 3# # 'user.attribute_a' 没有变化# # 'user.attribute_b' 没有变化# user.attribute_c = 'a_value'# 也许我应该做类似以下的事情,但是# 因为必须使用 'send' 方法,所以不起作用(下面的代码行# 只是我想做的一个例子).## user.send(:"#{attr}") = 'a_value'结尾...结尾

如何改进上面的代码以实现我的目标(我指的是user.send(:"#{attr}") = 'a_value' 部分为了以编程方式"设置 - 即为每次迭代设置不同的属性值 - 每个用户属性值为 'a_value')?

解决方案

你应该使用 .send 并在方法名后附加一个 = 来调用 setter,传递作为 send 的第二个参数的值:

<预><代码>[:attribute_a,:attribute_b,:attribute_c].each 做 |attr|在做之前user.send("#{attr}=", 'a_value')结尾

你正在有效地这样做:

user.send('attribute_a=', 'a_value');

由于以下几个原因,您的语法 (user.send(:"#{attr}") = 'a_value') 是错误/奇怪的:

  • 没有理由将 :attr 转换为字符串并立即将它们转换回符号
  • 你不能给.send的返回值赋值

I am using Ruby on Rails 3.0.9 and RSpec 2. I am trying to refactoring some spec file in the following way (in order to test with less code similar class object attribute values):

[
  :attribute_a,
  :attribute_b,
  :attribute_c
].each do |attr|
  before do
    # HERE I would like to set the "current" 'attr' related to the
    # class object instance 'attribute_< letter >' (read below for
    # more information) each time the iterator is called (note: all
    # following attributes are NOT attr_accesible - for that reason
    # I use the 'user.attribute_< letter >' in the 'before do'
    # statement)
    #
    # # Iteration 1
    #     user.attribute_a = 'a_value'
    # # No changes to 'user.attribute_b'
    # # No changes to 'user.attribute_c'
    #
    # # Iteration 2
    # # No changes to 'user.attribute_a'
    #     user.attribute_b = 'a_value'
    # # No changes to 'user.attribute_c'
    #
    # # Iteration 3
    # # No changes to 'user.attribute_a'
    # # No changes to 'user.attribute_b'
    #     user.attribute_c = 'a_value'

    # Maybe I should make something like the following but that, as well
    # as the 'send' method must be used, doesn't work (the below code-line
    # is just an example of what I would like to do).
    #
    # user.send(:"#{attr}") = 'a_value'
  end

  ...
end

How can I improve the above code so to accomplish what I aim (I refer to the user.send(:"#{attr}") = 'a_value' part in order to set "programmatically" - that is, set a different attribute value for each iteration made - each user attribute value to 'a_value')?

解决方案

You should use .send and append an = to the method name to invoke the setter, passing the value as the second argument to send:

[
  :attribute_a,
  :attribute_b,
  :attribute_c
].each do |attr|
  before do
    user.send("#{attr}=", 'a_value')
  end

You're effectively doing this:

user.send('attribute_a=', 'a_value');

Your syntax (user.send(:"#{attr}") = 'a_value') is wrong/weird for a couple reasons:

  • There's no reason to convert :attr to a string and them immediately back to a symbol
  • You can't assign a value to the return value of .send

这篇关于如何“以编程方式"\“以迭代方式"设置每个类对象属性都有一个值?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆