From: Eric Christopherson Date: 2013-03-06T04:14:16+09:00 Subject: Re: How `next` works in ruby with `unless` ? On Tue, Mar 5, 2013 at 12:53 PM, Robert Klemme wrote: > On Tue, Mar 5, 2013 at 7:38 PM, Hans Mackowiak wrote: >> Robert Klemme wrote in post #1100233: >>> On Tue, Mar 5, 2013 at 7:23 PM, wrote: >>>>> executed. Why does next not skip this statement ? >>> Probably because arguments are always evaluated before the "method" >>> they are handed over to. >>> >>>> Nobody writes code like this, so why care. >>> >>> I wasn't even aware that next accepts an argument - funnily it won't >>> accept two (syntax error). > >> hm it does: >> >> [1,2,3,4].map {|d| next d,4,5;p "is not printed" } >> #=> [[1, 4, 5], [2, 4, 5], [3, 4, 5], [4, 4, 5]] > > Oh, I tested only with brackets. Here's the whole story > > $ ruby -ce 'f { next }' > Syntax OK > $ ruby -ce 'f { next 1 }' > Syntax OK > $ ruby -ce 'f { next 1, 2 }' > Syntax OK > $ ruby -ce 'f { next 1, 2, 3 }' > Syntax OK > $ ruby -ce 'f { next(1) }' > Syntax OK > $ ruby -ce 'f { next(1, 2) }' > -e:1: syntax error, unexpected ',', expecting ')' > f { next(1, 2) } > ^ > > It's getting weirder - especially since the value(s) passed to next > are not used for anything as far as I can see. And it wouldn't make > sense, would it? I mean, next is different from break which can be > used to return a value from an iteration. `next val` causes an exit from a block, returning val. In a block passed to Kernel#loop, the value is discarded; so Kumar's `next puts 'hi'` just causes 'hi' to be printed but the nil return value of puts is discarded. `break val` also exits from a block, returning val, but in some cases also exits from the method calling the block. I wrote a test case for this on my work computer, but I don't have access to it here; but I seem to recall that break in a lambda simply exits the block, while break in a proc exits the method. (If you create the proc by passing a block to Proc.new, and then pass that proc to another method, which calls it, break will raise a LocalJumpError, since the original stack frame of Proc.new no longer exists.)