7

一般来说,学习 ruby​​ 和 oop,我遇到了类方法,据我所知,它们类似于实例方法,但是是从类而不是从对象访问的,并且只能同时运行一个。

但是,我不明白为什么您会使用类方法而不是普通方法(在类之外),它们的用途是什么?

例如:

#Why would you use:
class Foo
  def self.bar
    puts "Class method"
  end
end

#Versus simply:
def bar
  puts "Normal method"
end

Foo.bar # => Class method
bar # => Normal method

因为它们都产生相同的结果?我对他们很困惑,所以如果我误解了这里的任何/一切,请纠正。

4

5 回答 5

13

Your example isn't a good one.

Class methods might deal with managing all instances that exist of a class, and instance methods deal with a single instance at a time.

class Book
  def self.all_by_author(author)
    # made up database call
    database.find_all(:books, where: { author: author }).map do |book_data|
      new book_data # Same as: Book.new(book_data)
    end
  end

  def title
    @title
  end
end


books = Book.all_by_author('Jules Vern')
books[0].title #=> 'Journey to the Center of the Earth'

In this example we have a class named Book. It has a class method all_by_author. It queries some pretend database and returns an array of Book instances. The instance method title fetches the title of a single Book instance.

So the class method managing a collection of instances, and the instance method manages just that instance.


In general, if a method would operate on a group of instances, or is code related to that class but does not directly read or update a single instance, then it probably should be a class method.

于 2013-08-27T17:39:41.073 回答
3

这更像是一个 OOP 问题,而不是一个红宝石问题。ruby 中的类方法的使用与其他 OO 编程语言中的相同。这表示:

  • 类方法在类的上下文中运行(并且只能访问类变量)
  • 实例方法在对象的上下文中运行(并且可以访问对象或实例变量)

这是一个更好的例子:

class Foo
  def self.bar
    puts 'class method'
  end

  def baz
    puts 'instance method'
  end
end

Foo.bar # => "class method"
Foo.baz # => NoMethodError: undefined method ‘baz’ for Foo:Class

Foo.new.baz # => instance method
Foo.new.bar # => NoMethodError: undefined method ‘bar

在这里可以看到类方法是通过类来访问的,而实例方法是通过类的实例或对象来访问的(Foo.new)。

示例从此处复制,您还可以在此处找到有关此主题的更多信息。

请记住:尽管任何代码都可以放入类或实例方法中,但每个代码都有自己的用例和优缺点。在 OOP 中,我们力求可重用、灵活和可读的代码,这意味着我们通常希望将大部分代码作为实例方法结构化,放在一个合理的领域模型中。

于 2013-08-27T17:43:56.670 回答
3

正如你所说,它们是:

  • “从类而不是从对象访问,并且”
  • “只能同时运行一个。”

还要记住,该类是可移植的

于 2013-08-27T17:28:22.740 回答
0

你有很多误会,

在 ruby​​ 中,我们可以定义类和实例方法。

类方法用于在类级别提供处理,即只能在类级别可用或与所有对象相关的数据。例如,要计算属于类的对象的数量,您需要类方法。喜欢

Foo.count  

同样,要处理单个对象,您需要对象方法来处理单个对象,例如,

obj.save

因此,类方法是单调设计模式的示例,其中对象可以有自己的相同方法的实现。

于 2013-08-27T17:37:00.427 回答
0

最重要的是它使您的代码保持井井有条。当您拥有数十万行代码时,让它们都在同一个命名空间中随意乱扔东西可能会成为一场噩梦。组织非常重要,命名空间是在语言支持下获得模块化的简单方法。

不太重要的是,类/模块方法可以共享状态而不会到处泄漏(例如,类可以具有实例变量),并且它们可以具有私有支持方法以允许更好的分解,而全局方法不能有效地设为私有.

于 2013-08-27T17:34:07.803 回答