談談Ruby中的block
在Ruby語言中我們常常會用到block,那到底什麼是block呢? 其實block是ruby用來實現closure的一個方式,而closure是指將一段程式碼以匿名的方式先儲存起來,等到需要用的時候再去執行。這樣就會賦予我們的程式碼更多的彈性。
用#each
來當例子:
在這邊我們可以把這段程式碼拆成三個部分:
receiver: 陣列[1,2,3]
method: each
方法
block: do |ele| puts ele end
#each
方法在上面的這個例子中會將個別的元素印出來一次,並回傳原本的陣列。block在這個each
方法扮演什麼角色呢?我們可以實作一個each
方法來說明,以下程式碼是以模仿Array#each
為目的來實做一個自己的each
方法。
在以上程式碼可以看到,yield
關鍵字是block在each
方法裡被執行的地方,因此我們可以在不同的情境下傳不同的block進去。這個做法使得each方法非常有彈性,因為我們可以根據我們的需要傳入不同的block進去方法裡。
在Ruby中所有的方法都可以接受block作為參數,但除非方法實作裡面有yield
,否則block裡面的程式碼不會被執行。另一個狀況是方法實作裡面有yield
,但是呼叫方法的時候卻沒有給block,這時候如果執行方法的話,會跑出錯誤訊息”no block given (yield) (LocalJumpError)”
。如果要讓此方法在呼叫的時候沒有加入block也能正常執行的話,我們可以在yield
那邊加入一個條件式判斷Kernel#block_given?
。有傳入block的話yield
才會執行。
基本的block該注意的地方大概就是這些。除了block之外,在Ruby裡面還有兩種實現closure的方法,分別是Proc以及Lambda,而這又是另一段故事了…