我有用于多个虚拟属性的相同 getter/setter 代码 - 我可以使用 eval 进行重构吗?

发布于 2024-11-07 15:22:44 字数 969 浏览 4 评论 0原文

我为虚拟属性编写了自定义的 getter 和 setter 方法,将小数转换为整数以存储在数据库中。这是从数据库中的真实属性 (annual_fee) 获取/设置的三个虚拟属性 (annual_fee_dollars) 之一:

def annual_fee_dollars
  @annual_fee_dollars || int_to_dec(annual_fee)
end

def annual_fee_dollars=(string)
  @annual_fee_dollars = string
  self.annual_fee = dec_to_int(string)
end

与其重复所有这些代码三次,这是否有意义/是否安全/是否是“Rails”像这样重构代码的方式:

def self.decimal_get_and_set(variable, suffix)
  eval (
    "def #{variable + suffix}
      @#{variable + suffix} || int_to_dec(self.#{variable})
    end
    def #{variable+suffix}=(string)
      @#{variable+suffix} = string
      self.#{variable} = dec_to_int(string)
    end")
end
self.decimal_get_and_set "annual_fee", "_dollars"
self.decimal_get_and_set "interest_purchase", "_percent"
self.decimal_get_and_set "interest_cash", "_percent"

或者是否有更简洁的方法来构建此类功能?

如果这是一个“主观问题”,我深表歉意。在某种程度上,所有重构问题都具有一定的主观性,但我认为这个问题仍然有一席之地。很高兴对此进行纠正。

干杯!

I have written customised getter and setter methods for virtual attributes to convert decimals into integers for storage in a database. This is one of three virtual attributes (annual_fee_dollars) that get/sets from a real attributes (annual_fee) in the database:

def annual_fee_dollars
  @annual_fee_dollars || int_to_dec(annual_fee)
end

def annual_fee_dollars=(string)
  @annual_fee_dollars = string
  self.annual_fee = dec_to_int(string)
end

Instead of repeating all this code three times, does it make sense to / is it safe to / is it the 'Rails Way' to refactor the code like this:

def self.decimal_get_and_set(variable, suffix)
  eval (
    "def #{variable + suffix}
      @#{variable + suffix} || int_to_dec(self.#{variable})
    end
    def #{variable+suffix}=(string)
      @#{variable+suffix} = string
      self.#{variable} = dec_to_int(string)
    end")
end
self.decimal_get_and_set "annual_fee", "_dollars"
self.decimal_get_and_set "interest_purchase", "_percent"
self.decimal_get_and_set "interest_cash", "_percent"

Or is there a much cleaner way to build this type of functionality?

Apologies if this is a 'subjective question'. In part, all refactoring questions have some subjectivity to them, but I think this question still has a place on SO. Happy to be corrected on this.

Cheers!

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

后来的我们 2024-11-14 15:22:44

我认为你的方法很好,但我不建议使用 eval,主要是因为已经有更合适的 ruby​​ 元编程方法来做到这一点。阅读 define_method 的文档并对象方法 instance_variable_getinstance_variable_set

看起来像你想要的,你不需要自己使用 eval 。我可能会建议如下内容,但你是对的 - 所有重构问题本质上都有些主观。祝你好运!

{'annual_fee' => '_dollars', 'interest_purchase' => '_percent', 'interest_cash' => '_percent'}.each_pair do |variable, suffix|
  # Define getters
  define_method "#{variable+suffix}" do
    instance_variable_get("@#{variable+suffix}") || int_to_dec(send("#{variable}")
  end

  # Define setters
  define_method "#{variable+suffix}=" do
    ...
  end
end

I think your approach is fine, but I wouldn't suggest using eval, mainly because there is already a more appropriate ruby metaprogramming way to do this. Read up on the documentation for define_method and the object methods instance_variable_get and instance_variable_set.

Looks like what you want and you don't need to use eval yourself. I would probably suggest something like the following, but you're right - all refactoring questions are somewhat subjective by their very nature. Good luck!

{'annual_fee' => '_dollars', 'interest_purchase' => '_percent', 'interest_cash' => '_percent'}.each_pair do |variable, suffix|
  # Define getters
  define_method "#{variable+suffix}" do
    instance_variable_get("@#{variable+suffix}") || int_to_dec(send("#{variable}")
  end

  # Define setters
  define_method "#{variable+suffix}=" do
    ...
  end
end
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文