From: Robert Klemme Date: 2010-11-04T00:17:50+09:00 Subject: Re: Strange whitespace parsing behavior on Ruby 1.8.7 (patchlevel 249/302) On Wed, Nov 3, 2010 at 4:07 PM, Colin Bartlett wrote: > On Wed, Nov 3, 2010 at 5:45 AM, Ehsanul Hoque wrote: > >> >> That makes sense. But the inconsistency between the different behaviors >> given just a small difference in whitespace is still quite off-putting. >> >> Also how is this line parsed?: >> >> x.slice(1, x.size -2) >> >> - It seems unreasonable to parse it any way other than that intended.Insert >> mode >> > > Subject to correction by Robert - or anyone else! - to summarise I think the > basic problem for Ruby here is when to parse "-2" (without any space between > the "-" and the "2") as a unary operator on 2 and as a binary operator on a > previous "token" with 2 as the argument. > > At one extreme, Ruby could raise an error if there is any possible > ambiguity. Ruby, I think, tries to do the best it can with *limited* > knowledge of the methods being interpreted. > > For example: >  7 -2 => 5 > this works for a similar reason to the reason this works: >  x = 13 >  x -2 #=> 11 > Ruby knows (or anyway interprets) x as a variable, not a method, so no > ambiguity: the "-" is either a mistake or is a binary operator. I think the Ruby interpreter _knows_ it because during parsing it recognizes "x = 13" as a local variable assignment which makes x a local variable and will shadow method x (if it exists). That knowledge might also be used to disambiguate "x -2" which does not really make sens with a local variable if not interpreted as an expression with a binary "-". >  x.size #=> 4 >  x.size-3 #=> 1 > I'm guessing that here Ruby "thinks" no whitespace, so bind the "-" to the > first possible token, which is (x.size), so "-" gets treated as a binary > operator. > > But in: >  x.size -2 > this could mean > ((x.size) - 2) or (x.size( -2 )) > In this case size doesn't take any arguments, so with some more work the > interpreter could parse it as being likely to be ((x.size)-2), but that > won't work for methods which can take zero or one (or more) arguments. > So (again a guess) the idea is that the interpreter won't even try to to > some extra work which might, or might not, resolve the ambiguity. > > The result is what seems to me to be a reasonable compromise, but I ought to > add that some other possibilities might also be a reasonable (but different) > compromise! Absolutely agree. I'd also like to add that this has never been an issue for me in practice. So we are probably putting something under a microscope which is actually really small. :-) Cheers robert -- remember.guy do |as, often| as.you_can - without end http://blog.rubybestpractices.com/