Monday, May 28, 2012

Lambda Function syntax in Ruby 1.9

Tonight's head-banging incident was directly related to lambda function syntax.  Rather naively I assumed that what I thought would work would work.  As always, assumption makes an ass out of umption.

This works as I would expect
# a simple no-argument lambda
y = -> { 1 * 2 }

This works as I would expect, too
# a lambda that takes one argument and doubles it
z = ->(a) { a * 2}
puts z.(1)
=> 2

However, the important thing to realize is that lambda definitions are whitespace sensitive, whereas a lot of the rest of the language does not seem to be.
 
#     v  <-- note the space below the v
x = -> (a,b) { a * b * 3 }

Ruby really, really doesn't like this space:
C:\Ruby193\bin\ruby.exe -e $stdout.sync=true;$stderr.sync=true;load($0=ARGV.shift) C:/workspace/ruby-intro/rubymine-intro/modules/closure.rb
-e:1:in `load': C:/workspace/ruby-intro/rubymine-intro/modules/closure.rb:5: syntax error, unexpected tLPAREN_ARG, expecting keyword_do_LAMBDA or tLAMBEG (SyntaxError)
x = -> (a,b) { a * b * 3 }
        ^
    from -e:1:in `<main>'

So remember, lest you also spend some frustrated time going 'WTF' at the ruby interpreter.  Lambdas which take method arguments are WHITESPACE SENSITIVE.

See This StackOverflow question (Spacing around parentheses in Ruby) for more information.

Introduction and Reasoning

I am an experienced Java developer who is now making the jump into a Ruby environment.  I have a passing familiarity with Python, thanks to lots of time spent on ProjectEuler.net.  However, I have never used Ruby itself.

During my initial investigations of the language I have discovered things which strike me as odd when viewed from a perspective of a non-Ruby user.  Some of these seem ridiculous, some are no doubt by design.

Also, it's often not easy to find out why certain things are the way they are.

My plan is to document what I discover here, with links which will hopefully not go out of date too soon.