iT邦幫忙

DAY 28
0

Ruby女孩:10萬.times { puts "為什麼?" }系列 第 28

Ruby女孩(28):慢慢打開區塊引數的包裝

  • 分享至 

  • xImage
  •  

昨天提到的引數有好幾種,今天要來介紹Ruby常用的block引數:『區塊引數』

區塊是什麼呢?本篇文章只有先撥開一點點它的包裝,更深入的內容還有待之後分享!

這次鐵人賽的主題就是使用區塊的一例子:

10萬.times { puts "為什麼?" }

times是Integer的實體方法,怪了,我們昨天說過,方法的後面接的應該是個圓括號,圓括號的裡面會放入引數,但這個times方法後面卻接著長得很像雜湊(Hash)的東西,這到底是啥?

好的,先不要把這個跟雜湊搞混了,我們以前在Ruby女孩(11)中提到的雜湊,雜湊是長這樣的:

{:name => "Annie",:age => 99}

{name: "Annie", age: 99}

很明顯你在雜湊中會看到一對一對的鍵(Key)值(Value),與Numeric、String與Array一樣都是Ruby中的資料型別。但今天所要認識的『區塊(block)』,它並不是另一種資料型別,它是迭代器的基礎,我們接下來會好好認識它是怎麼運作,而方法要如何調用它?

※ 區塊的語法

1. 區塊不能單獨存在,它一定要伴隨著方法調用。
2. 可以用大括號{}或是do和end當作區塊的起始與終止。
3. 但左括號{或do,一定要跟方法名稱放在同一列。
4. 有一慣例,當區塊方法只有一行時,使用{};若超過一行,則使用do/end。

1.upto(10) { |x| puts x }

1.upto(10) do |x|
  puts x
end

5. 如果想省略圓括號,要小心!請看以下範例:

1.upto(10) {|x| puts x}     #正常執行
1.upto 10 do |x| puts x end #正常執行
1.upto 10 {|x| puts x}      #SyntaxError

區塊會找緊接著它的方法試圖傳進去,第三種會出現SyntaxError,就是因為它以為緊跟著它的方法是10,才會噴錯!所以若想省略方法的圓括號,請改以do/end撰寫。不然就不要省略!!

6. 區塊本身也可以類似方法而有多個參數,例如:

test.each { |x,y,z| puts "#{x}、#{y}、#{z}" }

7. 區塊本身的參數也有一慣例寫法,會跟左括號{或do寫在同一行。

OK,看完區塊的基本規則,我們來了解一下該如何在方法的引數中傳入區塊。

※ 傳遞區塊引數

由於區塊是不具名稱的,他們的調用是要前綴一個『&』符號,而且規定一定要寫在引數的最後一個!實際使用的方式如下:

def test(a,b,*c,&d)
  puts "a=#{a}"
  puts "b=#{b}"
  puts "c=#{c}"
  d.call(5)
end

test(1,2,3,4,5){|n| n.times{puts "ruby"}}

a=1
b=2
c=[3, 4, 5]
ruby
ruby
ruby
ruby
ruby

你可以注意到,我們在方法後面直接丟入了一個區塊作為&d的引數,並且在方法中,用.call來給予區塊本身的區塊參數!那.call這個方法是誰的方法呢?我們可以用這個方法看看區塊到底是誰?

def who_am_i(&block)
  "我其實是#{block.class}"
end

who_am_i{}
=> "我其實是Proc"

好像解謎一樣,一層一層把區塊的秘密掀出來XD原來區塊是Proc,Proc和Lambda是另一組容易被搞混的詞,這個部分我得好好吸收一下才知道怎麼寫出來不會誤導大家!有待明天揭曉XD

最後補充一個書上目前沒看到的傳遞引數的方式:

def sum(a, *b, **c, &d)
  puts "a=#{a}"
  puts "b=#{b}"
  puts "c=#{c}"
  d.call(100)
end
sum(1,2,3,4,5,x:6,y:7) { |x| puts x }

a=1
b=[2, 3, 4, 5]
c={:x=>6, :y=>7}
100

有看見上面的c前綴的是『**』,與『*』不同的是,『**』可以傳進雜湊的值,也因此你才可以看到上面puts c之後的結果!

=================================================

28天!

“Decide that you want it more than you are afraid of it.”

雖然讀的內容越來越深,但想學的心還是大於害怕!加油加油!


上一篇
Ruby女孩(27):方法的引數傳遞方式,你覺得很簡單嗎?進來小試身手看看XD
下一篇
Ruby女孩(29):揭開區塊的面紗-Proc、lambda
系列文
Ruby女孩:10萬.times { puts "為什麼?" }30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言