2012-02-13 22 views
1

好像如果你正在尋找能夠調用一個模塊(/班),你正在尋找一個單身方法......如果是這樣的話,你使用類方法或Singleton的更好mixin(不尋找答案,哪一個是「更好」)。Module#module_function被認爲是壞的嗎?

唯一的好處(?)我可以使用#module_function看到的是模塊以及模塊上調用方法在混合的靈活性。還有別的事嗎?

我發現一些舊代碼,用來工作< 1.9.3跑,但不會再和我期待解決。它看起來是這樣的:

module MyThing 
    def self.do_something 
    ... 
    end 
end 

...並允許:

MyThing.do_something 

我並不想爭辯說,這樣的設計是一個很好的 - 只是試圖找出什麼最好的辦法是解決它。傾向於一個標準模塊...

更新...

我錯誤地簡化了我的問題和榜樣。我正在經歷的不同行爲是在我的RSpec測試期間 - 他們通過使用RSpec 2.8.0和MRI 1.9.2,但通過MRI 1.9.3失敗。該模塊的樣子:

module MyThing 
    module SubThing 
    module SubSubThing 
     def self.do_something 
     ... 
     end 
    end 
    end 
end 

...和測試:

describe MyThing::SubThing::SubSubThing do 
    include MyThing::SubThing 

    describe "#do_something" do 
    it "does something" do 
     SubSubThing.do_something 
    end 
    end 
end 

在1.9.3下運行的規範,我得到NameError: uninitialized constant DataGathering;在1.9.2下,他們通過。這導致我錯誤地診斷問題,並呈現我在上面做了什麼。好像include行爲在1.9.3中不同。沒關係;我的問題仍然存在:#module_function提供了一些特別的東西嗎?

+2

你舉的例子在這裏工作 - 運行紅寶石1.9.3dev(2011-09-23修訂33323)x86_64的-darwin11.0.0。 – user2398029 2012-02-13 19:10:25

+0

感謝您的檢查;這讓我意識到我錯誤地診斷了這個問題。我已更新以描述真正的問題。 – turboladen 2012-02-13 21:48:20

+1

FWIW,看起來像我的1.9.2 v。1.9。3問題被記錄爲[1.9.3錯誤](http://bugs.ruby-lang.org/issues/5657)(最初[由Matz記錄](http://bugs.ruby-lang.org/issues/4536)),但結果是一個1.9.2的錯誤。去搞清楚。 – turboladen 2012-02-14 00:54:59

回答

3

module_function目的正是你在你的問題中提到:它給你的靈活性,顯式調用模塊類方法,使用模塊名,或給它的混合,使事情更簡潔一點。

你也可以做extend self同樣的事情(模塊定義中)。不同之處在於,如果混合使用module_function的模塊,混合方法將變爲私有實例方法(但它們將是聲明模塊的公共類方法);如果你使用extend self,他們將擁有的任何訪問限定符在模塊定義中使用,既混合,並當模塊作爲類方法的直接調用。

+0

我只是在'irb'中做了一些快速測試,並更正了我的答案。 – 2012-02-13 22:31:29

+0

回頭看這篇文章,我可以補充一點,我認爲'Singleton' mixin(因爲OP提到它)幾乎沒用。如果你想要一個「singleton」,只需創建一個新對象(使用Object.new'),並定義你需要的任何方法。 – 2013-01-19 19:01:23

0

Ruby中的模塊抽象地等同於C++中的Namespace。這應該對Ruby 1.9.3罰款:

module MyThing 
    def MyThing.do_something 
     # ... 
    end 
end 

do_something也可以作爲MyThing的實例方法,這就是事情變得明朗實施。

+0

你是對的;我錯誤地描述了我的問題。相應更新。 – turboladen 2012-02-13 21:47:34

相關問題