何时在Ruby方法中使用`self.foo`而不是`foo`

时间:2011-01-15 12:57:22

标签: ruby self

这不是Rails特有的 - 我只是以Rails为例。

我在Rails中有一个模型:

class Item < ActiveRecord::Base

  def hello
    puts "Hello, #{self.name}"
  end
end

(假设Item模型(类)有一个名为name的方法。我何时需要使用self.name,何时才能使用name? (例如#{name}

3 个答案:

答案 0 :(得分:59)

  1. 在调用方法时, prefer 忽略self.是惯用的;通常不需要它。

  2. 必须 在调用setter方法而不是self.foo = xxx时使用foo = xxx,以便Ruby意识到您不是尝试创建一个新的局部变量。

    • 同样,如果您有一个与方法同名的现有局部变量do_something,则必须使用self.do_something来调用该方法,因为{{1最终会读取变量。
  3. 无法 使用do_something来调用私有方法;您必须只调用self.foo(...)

答案 1 :(得分:10)

如果省略self Ruby将首先查找具有该名称的局部变量,然后查找实例方法。写self.并不是惯用语。无论如何,你必须在作业上写self.something = value

请注意,在调用私有方法时不能使用self(受保护方法没有问题):

class A
  def foo; self.bar; end

private

  def bar; "bar"; end
end

A.new.foo  
# private method `bar' called for #<A:0x7f49193584f0> (NoMethodError)

答案 2 :(得分:0)

关注this tutorial,您无需使用 self 指针。但我认为这个(或者我们案例中的 self )指针用于解决名称冲突。实际上,@nameself.name是相同的陈述(如果您的班级没有name方法)。 E.g:

class Moo
  attr_accessor :name

  def moo(name)
    name = name # O_o which *name* should i use?
  end

  def foo(name)
    @name = name # the same as *self.name = name*
  end

  def hello
    puts self.name # the same as *puts @name*
  end
end

a = Moo.new
a.hello() # should give no output

a.moo('zaooza')
a.hello() # Hey! Why does it prints nothing?

a.foo('zaooza')
a.hello() # whoa! This one shows 'zaooza'!

尝试运行此代码,您会看到=)