Какова цель методов экземпляра в модулях без классов? - PullRequest
9 голосов
/ 02 октября 2008

Представьте себе следующий модуль Ruby:

module Foo
  def inst_method
    puts "Called Foo.inst_method"
  end
  def self.class_method
    puts "Called Foo.class_method"
  end
end

Очевидно, Foo.class_method можно вызывать без каких-либо экземпляров классов. Однако, что происходит с Foo.inst_method? Можно ли вызвать Foo.inst_method без предварительного включения / расширения класса?

Отказ от ответственности: Вопрос не в том, чтобы решить реальную проблему. Я просто пытаюсь улучшить свое понимание объектной системы Ruby.

Ответы [ 2 ]

12 голосов
/ 02 октября 2008

Основная цель методов экземпляра в модулях состоит в том, чтобы предоставить эту функциональность классам, которые ее включают.

«Вмешивание» в модуль таким образом чаще всего используется как метод имитации множественного наследования , или в других ситуациях, когда наследование - это не правильная парадигма (не совсем идеальное «это» отношение ) но вы хотите поделиться поведением. Это еще один инструмент для сохранения вашего кода DRY .

Хорошим примером этого в ядре Ruby является то, как Array и Hash можно перемещать и сортировать и т. Д. Каждый из них получает эту функциональность от Enumerable модуль (each_with_index, select, reject, sort и другие определены в включенном модуле, а не в классах).

4 голосов
/ 02 октября 2008

Мой ответ будет: «Нет, вы не можете вызывать методы экземпляра модуля без предварительного расширения или включения этого модуля в класс»

теперь зная ruby ​​и все хитрости метапрограммирования, которые он там содержит, вероятно, - это способ его вызова, но он не входит в предполагаемое использование модулей

module Tester
  def inst_meth
    puts "test inst meth\n"
  end

  def self.meth
    puts "test self meth\n"
  end
end

begin
  Tester.meth
rescue;
  puts $!
end
begin
  Tester.inst_meth
rescue
  puts $!
end
begin
  Tester.new.inst_meth
rescue
  puts $!
end
begin
  extend Tester
  inst_meth
rescue
  puts $!
end
begin
  include Tester
  inst_meth
rescue
  puts $!
end

дает

>ruby test.rb
test self meth
undefined method `inst_meth' for Tester:Module
undefined method `new' for Tester:Module
 test inst meth
 test inst meth
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...