iT邦幫忙

第 12 屆 iThome 鐵人賽

DAY 17
0
自我挑戰組

滿滿的紅寶石不拿嗎?-- 去吧!我把世界上的一切都放在那裡了! 系列 第 17

Block <> 只是想被人需要,我很樂意為你執行! - 滿滿的紅寶石不拿嗎?

  • 分享至 

  • xImage
  •  

[Day17](謎:今天要用哪一張圖呢?)Baby5:明白!是需要我吧!


接著再介紹一個 Ruby 的重要概念(每個都很重要...結果就都不重要了)
anyway 要登場的就是 Block (鏘鏘!)
也可以稱作「(程式碼)區塊」,只是很少這麼叫它就是了。

雖然和數位金融領域近幾年很熱門的:區塊鏈(Blockchain) 兩者名字很像,但 Block 和 Blockchain 兩者完全不一樣,有興趣了解區塊鏈的朋友可以右轉到 TaiwanBar:

Yes

抱歉跑題了...
接著就開始介紹 Block 吧!希望能把它解釋清楚~


Block 是什麼?

首先,Block 是 Ruby 裡少數不是物件的存在,它也是一段不會被主動執行的程式碼,並且在實務上被大量地使用在 Rails 裡。

Block 有兩種表示方式:

  • 「大括號」寫法
{
  ... # Block 要做的事
}
  • do...end 寫法
do
  ... # Block 要做的事
end

看起來是不是有點像閹割版的方法?但其實不太一樣喔!


兩種寫法有什麼不同?

我們直接來看例子:

list = [1, 2, 3]

p list.map{ |i| i + 2 }        

# 印出
[3, 4, 5]


p list.map do |i| i + 2 end

# 印出
#<Enumerator: [1, 2, 3]:map>

What?! 為什麼會這樣?其實是因為 Ruby 語言經常會省略小括號 () ,實際上這兩行長成這樣:

list = [1, 2, 3]

p(list.map{ |i| i + 2 })        

# 印出
[3, 4, 5]


p(list.map) do |i| i + 2 end

# 印出
#<Enumerator: [1, 2, 3]:map>

由於 do...end 的優先級較低,所以先跟 p 結合了,後面的 Block 就被忽略了...(存在感真低啊)


那個 |i| 是什麼?

啊那個其實只是一個變數,通常會在要傳一個東西進到 Block 的時候使用,或是方法在轉讓控制權(yield)時帶出了參數,就可以把參數放進 Block 讓它去執行。

另外,在上面的例子裡不能省略,因為 |i| 在此代表著 list 陣列中的每一個值。

當然 |i| 只是個變數,要把它改成 abvalue 也行,不過裡面外面都要用同樣的名稱才行。


聽說 Block 無法獨自存活

因為 Block 無法在程式環境忍受孤獨(誤),如果只有 Block 存在的話會造成語法錯誤:

{
  puts "我是大括號型的 Block"
}

# 印出
#syntax error, unexpected '}', expecting end-of-input
do
  puts "我是 do...end 型的 Block"
end

# 印出
#syntax error, unexpected end, expecting end-of-input

以上兩種語法都沒辦法執行!


Block 過得也不是很好...

在程式裡,Block 必須依附在某個方法後面,只能寄居人下非常可憐,而 Block 會不會動(能否執行),要看所依附的方法同不同意讓 Block 執行,完全就是看人臉色的可撥仔!

我們來看看它被邊緣的模樣:

def jump(name)
  puts "#{name}跳起來!"
end

jump("喬巴") {
  puts "我是大括號型的 Block"
}

# do ... end 寫法
jump("喬巴") do
  puts "我是 do...end 型的 Block"
end

參數是name,而不是 Block

雖然執行上面這段程式碼不會有任何錯誤,但 Block 裡寫好的程式也不會執行...


那要怎麼讓 Block 動起來

如果要讓 Block 動起來,必須在方法裡加上一個 yield 才行:

def say_hello
  puts "安安, "
  yield
  puts "幾歲?"
end

say_hello {
  puts "你好!"
}
puts "住哪?"

# 印出
安安, 
你好!
幾歲?
住哪?

不過,要理解 Block 的運作原理,還必須知道 scopeyield 的概念才行。


今天就先到這邊啦!明天我會繼續說明 Block 的概念~

參考來源:
為你自己學 Ruby on Rails - 方法與程式碼區塊
五倍紅寶石 - Proc是什麼可以吃嗎


上一篇
符號 <> 看!又是一塊歷史正文!讀懂這些,通往 ONEPIECE 的路就不遠了!- 滿滿的紅寶石不拿嗎?
下一篇
scope <> 你已經進到「死亡外科醫生」的領域了!ROOM! - 滿滿的紅寶石不拿嗎?
系列文
滿滿的紅寶石不拿嗎?-- 去吧!我把世界上的一切都放在那裡了! 30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言