не Предположим, что у вас это:
class TestClass
module ClassMethods
attr_accessor :number
def initialize
@number = 47
end
end
include ClassMethods
extend ClassMethods
end
Давайте получить некоторую информацию об этом классе:
TestClass.instance_variables #=> []
никаких сюрпризов.
tc = TestClass.new #=> #<TestClass:0x00000101098a10 @number=47>
p tc.instance_variables #=> [:@number]
tc.number #=> 47
tc.number = 11
Все как ожидается. Переменная экземпляра @number
была создана initialize
, и мы можем проверить ее и изменить ее с помощью аксессора.
extend
TestClass#initialize
метод класса, но он не был вызван. Давайте вызвать его для инициализации экземпляра класса переменной @number
:
TestClass.initialize
#=> NoMethodError: private method `initialize' called for TestClass:Class
Ах, да, initialize
является частным методом.
TestClass.methods.include?(:initialize) #=> false
TestClass.private_methods.include?(:initialize) #=> true
Мы не можем использовать методы частного класса обычным способом. send
, однако, работает с частными и государственными методами:
TestClass.send :initialize #=> 47
TestClass.instance_variables #=> [:@number]
TestClass.instance_variable_get(:@number) #=> 47
Так что теперь переменная экземпляра класса был создан устанавливается равным 47
. Изменилось ли значение переменной экземпляра @number
?
tc.number #=> 11
Это не изменено. Теперь давайте изменим значение переменного экземпляра класса, а затем увидеть, если значение переменного экземпляра зависит:
TestClass.instance_variable_set(:@number, -5) #=> -5
tc.number #=> 11
Если вы хотите добавить аксессор для экземпляра класса переменной @number
, добавьте эту строку в класс или модуль:
Module.instance_eval("attr_accessor :number")
(Для объяснения см мой ответ here.)
Тогда тест:
TestClass.number #=> -5
TestClass.number = 107
TestClass.number #=> 107
Первое число для данного экземпляра 'TestClass'; вторая - переменная экземпляра класса.Они могут сосуществовать, поскольку они отличаются от «@ night» и «@ day». –
@CarySwoveland: Я это понимаю. Мой вопрос в том, почему «расширение ClassMethods» не инициализирует переменную экземпляра класса. И как я могу инициализировать переменную экземпляра экземпляра и класса без дублирования кода? – xx77aBs
xx, я не забыл. Мне просто потребовалось некоторое время, чтобы найти время, чтобы дать ответ. Дайте знать, если у вас появятся вопросы. –