假設我有一個模塊:如何從Ruby中的實例方法訪問模塊?
module M
def self.foo
...
end
def bar
...
end
end
M
模塊被包括在一類。
class A
include M
end
我想打電話給foo
從bar
,最終將上A
實例調用。在bar
內部完成此操作的最佳方法是什麼?
當然,我可以說M.foo
,但這是模塊名稱的重複,這是不必要的。
假設我有一個模塊:如何從Ruby中的實例方法訪問模塊?
module M
def self.foo
...
end
def bar
...
end
end
M
模塊被包括在一類。
class A
include M
end
我想打電話給foo
從bar
,最終將上A
實例調用。在bar
內部完成此操作的最佳方法是什麼?
當然,我可以說M.foo
,但這是模塊名稱的重複,這是不必要的。
通常,在module
,這是一個很好的做法,類方法和實例的方法分離出來,像這樣:現在
module M
def bar
puts "BAR"
self.class.foo
end
module ClassMethods
def foo
puts "FOO"
end
end
end
,在一個班,我會非常想include
這個模塊M
以一種方式,我得到A.foo
作爲類的方法和A.new.bar
作爲實例方法。這個技巧是Module.included
。
module M
def bar
puts "BAR"
self.class.foo
end
module ClassMethods
def foo
puts "FOO"
end
end
# when module is included, extend the class with ClassMethods
def self.included(base)
base.extend ClassMethods
end
end
class A
include M
end
A.singleton_methods #=> [:foo]
A.new.foo
#=> BAR
#=> FOO
通過這種方法,您可以參閱類方法與self.class
,它會自動地工作。
希望它有幫助。
謝謝,我沒有想到這個!由於似乎沒有避免在'A'中包含'foo'的解決方案,我明白爲什麼要感謝Jorg的評論,我會接受這個答案,因爲它最接近我想要的。 –
不是真的優雅,但
def bar
Module.nesting.last.foo
end
應該這樣做。
請注意Module#nesting
返回一個數組,因爲一個模塊可能嵌套到另一個模塊中。在一般情況下,你需要應用正確的數組索引來選擇你想要的模塊。
我認爲使用M.foo
是最好的,但作爲一個練習,可以按如下方式更改M#bar
。
module M
def self.foo
puts "In self.foo"
end
def bar
puts "In bar"
method(__method__).owner.foo
end
end
class A
include M
end
a = A.new
a.bar
# In bar
# In self.foo
考慮使用'__caller__'而不是'__method__'來使別名方法成爲可能,並使代碼仍然有效。 – mudasobwa
_「我想從酒吧叫foo」_ - 如果除了'M.foo'之外還有'A.foo',哪個'foo'想要打電話? – Stefan
爲什麼你不想使用'M.foo'?在我看來,這是合乎邏輯的事情。將類方法和實例方法放在同一個模塊中看起來很奇怪,考慮到你想調用第一個幷包含第二個。 –
「A」和「M」的單例類之間沒有任何關係。特別是,'M'的單例類不在'A'的繼承鏈中。 –