「Ruby 語法放大鏡」系列短文主要是針對在大家學習 Ruby 或 Rails 時看到一些神奇但不知道用途的語法介紹,希望可以藉由這一系列的短文幫大家更容易的了解到底 Ruby 或 Rails 是怎麼回事。
隨便打開你 Rails 專案裡的 model 檔案,它可能會長得像這樣:
1 2 3 4 | |
第一行後面那個 ActiveRecord::Base 裡面的 2 個冒號 ::,各位知道是什麼意思嗎?
菜市場名
也許你也叫金城武(或自己覺得自己長得像金城武),然後我也剛好也很巧叫金城武,這樣在大街上大叫一聲帥哥就一堆人回頭了,不太好。
寫程式偶爾也會遇到這樣的狀況,舉例來說,如果大家剛好都有一個叫做 Animal 的類別或是 Flyable 的模組,放在同一個專案裡就會打架了。所以 Ruby 有設計 namespace 來解決這個問題。
在 Ruby 裡,因為 module 或 class 可以有巢狀結構(類別裡可以包模組,模組裡面可以包類別,就是大腸包小腸的概念啦),剛好可以拿來做 namespace 的包裝,例如:
1 2 3 4 5 6 7 | |
這樣一來,如果要使用 Flyable 這個類別的話:
1 2 3 | |
要 include 那個 Flyable 模組,就必須連名帶姓的 include,也就是「樹林::金城武」、「三重::劉德華」的概念。
除此之外,其實你也可把常數包在 namespace 裡:
1 2 3 4 5 6 7 8 9 10 11 12 | |
要使用這些常數,也是一樣要提供完整的路徑給才行。(如果你知道的話,其實不管是類別或模組,它們的名字基本上也就是常數而已)
所以,原來這段程式範例:
1 2 3 4 | |
它的意思就是說有一個叫做 Post 的類別,它是繼承自某個放在 ActiveRecord 的模組(或類別)裡的 Base 類別。如果去 github 上翻 Rails 的原始碼的話(連結),應該可以看到這段:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | |
的確是有一個 ActiveRecord 的模組,裡面包了一個 Base 的類別沒錯 :)