繁体   English   中英

方法与属性Rails

[英]Methods vs Attributes Rails

今晚与我的一位同事就Rails中的方法与属性进行了辩论。 我发誓除非我疯了,否则我以前见过。 这是一个例子:

我们有一个用户模型,我们想确定在保存记录之前我们有一个名字和一个姓氏。 我讨厌回调,但是对于此示例,假设它在before_save回调中。

class User     
  before_save :set_first_last

  def set_first_last
    first_name if self.first_name.blank?
    last_name if self.last_name.blank?
  end

  def first_name
    self.first_name = self.name.split(" ").first
  end

  def last_name
    self.last_name = self.name.split(" ").last
  end
end

因此,我很好奇是否调用了方法“ set_first_last”,并且看到用户的属性first_name为空,它将调用方法“ first_name”,对吗? 用户的属性first_name与称为“ first_name”的方法不同。 因此,在用户对象上名为“ first_name”的属性与在Rails中称为“ first_name”的用户类上的方法会不同吗? 这就像一个类级别的方法还是实例方法? 只是想确保我是正确的,并且我正在正确地解释这一点。

谢谢

- 麦克风

我认为您误读了以下代码:

def set_first_last
  first_name if self.first_name.blank?
  last_name if self.last_name.blank?
end

此代码调用first_name方法,如果为空,则再次调用first_name方法(换句话说,该方法的if部分毫无意义)

构造此代码的方式,将永远不会使用first_name和last_name属性的值(除非您要在查询中使用它们)-任何时候执行user.first_name都会从name重建它。 一种更常见的模式是使用设置名称的方法,如ensure_first_name (基本上是任何不使用getter进行分类的东西)

实例变量(例如@foo)与同名方法不同,尽管foofoo=当然是获取/设置该名称实例变量的方法,这是很常见的。 也许您在想那件事? 在这种情况下,Activerecord模型的属性不会存储在单个实例变量中。

要回答我认为我理解的部分:是的,模型上的属性与方法完全不同。

以一个用户模型,一个用户控制器及其对应的视图之一为例。 假设用户模型本身包含first_namelast_nameemail属性:

class User < ActiveRecord::Base
  #Ensure presence of the following before saving model
  validates_presence_of :first_name, :last_name, :email 

  #Verify unique email
  validates_uniqueness_of :email

  #Here's our lone User method...poor guy
  def admin?
    self.company_members.where('? = ANY (company_members.roles)', Role::ADMIN).any?
  end
end

当您开始在控制器中使用该模型的实例时,它将看起来像这样:

class UsersController < ApplicationController
  def index
    #Let's just grab a random user
    @user = User.find(1)
  end
end

最后,在您看来,可以通过以下方式访问您的属性(属性):

####views/users/index.html.haml####

.random-class
  = "You're logged in as #{@user.first_name}!"

但是我们也可以在视图中调用User 方法 继续上一个示例,我们可以添加如下内容:

####views/users/index.html.haml####

.random-class
  = "You're logged in as #{@user.first_name}!"
  - if @user.admin?
    = 'Oh my gosh, our freaking User method worked!'

简而言之,您的正确之处在于属性和方法有很大的不同,尽管它们有时看起来很相似。

最后,值得指出的是,实例方法就是这样:方法是在类的实例上调用的,而类方法是在实际的模型对象上调用的,而不是在该模型对象的单个实例上调用的。 这是一个很好的链接,可了解更多有关差异的信息。

希望这可以帮助!

是的,您的解释是正确的。 您的代码将开始工作,并使用拆分后的形式分配first_name和last_name。 此外,您也可以通过这种方式编写代码(假设您的全名由2个单词组成,并用空格隔开)

 #user.rb
class user     
  before_save :assign_individual_names

 private 
  def assign_individual_names
    first_name, last_name = name.split(' ')
  end

end

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM