2013-07-23 67 views
31

這個Ruby 2.0代碼有什麼問題?意外的回報(LocalJumpError)

p (1..8).collect{|denom| 
    (1...denom).collect{|num| 
     r = Rational(num, denom) 
     if r > Rational(1, 3) and r < Rational(1, 2) 
      return 1 
     else 
      return 0 
     end 
    } 
}.flatten 

錯誤出現在block (2 levels) in <main>': unexpected return (LocalJumpError)。我想創建一個包含n的平板列表(其餘爲零),其中n是分母低於8的有理數的數目,介於1/3和1/2之間。 (it's a Project Euler problem)。所以我試圖從內部塊返回。

+2

不要在塊中使用'return'。只要刪除'return',你的代碼就可以了。 – oldergod

回答

37

您不能return在Ruby *的塊內。最後一條語句成爲返回值,所以你可以刪除你的情況return語句:

p (1..8).collect{|denom| 
    (1...denom).collect{|num| 
     r = Rational(num, denom) 
     if r > Rational(1, 3) and r < Rational(1, 2) 
      1 
     else 
      0 
     end 
    } 
}.flatten 

*:你可以在裏面lambda塊:lambda { return "foo" }.call # => "foo"。它涉及範圍界定和所有這些,這是lambda區塊和proc區塊之間的主要區別之一。您傳遞給方法的「正常」塊更像proc塊。

+55

您可以*在Ruby中使用'return'。它將從封閉的方法返回。在這種情況下,*沒有*封閉方法,*這是*爲什麼會出現錯誤,它不是*,因爲塊中的「return」是非法的。 –

+0

@JörgWMittag你說得對,我正在簡化。 'return'返回最近的方法*或*'lambda'塊,你在裏面。如果你不在裏面,你會得到一個'LocalJumpError'。 – henrikhodne

+0

@JörgWMittag謝謝你的澄清聲明。答案讓人困惑,你澄清了它。我現在明白爲什麼這個錯誤很容易出現在irb中。 –