Blocks != Functional Programming
Here’s what I realized: it seems that every language under the sun is being evangelized as an excellent functional programming language simply because it supports a few paradigms from FP.
Or, restated: Anonymous functions do not a functional language make.
The most egregious example of a pundit claiming a language is functional when it’s clearly not is Eric Kidd’s well-known Why Ruby is an acceptable Lisp. Kidd tells us explicitly that Ruby is a denser functional language than Lisp – and I’ll be the first one to admit that if I were to debate the “denser” part of that sentence, I wouldn’t know what I was talking about.
But Ruby is not functional – Wikipedia calls it a reflective, object-oriented programming language, and I agree with them. Yes, you can have block arguments to methods, continuations, generators, reflection, and metaprogramming – but it isn’t functional, for two reasons.
1. It’s hard to carry around functions as objects.
I really don’t know why Ruby hates parentheses so much – it’s probably part of its Perl heritage. In Ruby, you can call methods without sticking superfluous parentheses in there – take a look at this Python code:
" I'll write about Cocoa soon; disaster struck the app I was writing ".strip().lower().split()
Now take a look at the equivalent Ruby code:
" Apple's releasing a tool
with XCode 3
which completely supersedes my Cocoa app - so I'm very depressed right now ".strip.downcase.split
Though you could put parentheses in front of
split, Ruby will work just fine without them. Now, this feature makes for far fewer parentheses, thereby making code significantly more readable. But what if I want a previously-declared function as an argument? If I type in the name, Ruby will just evaluate the function. Sure, I could use the kludge that is Symbol.to_proc, but that’s ugly – and it wraps the function inside a Proc object, which has to be called with the
call(*args) method. And that’s just ugly. In Python, all you need to do is type the function’s name to use it as an object, and append a pair of parentheses if you need to call it.
2. Variables are.
A purely functional language only has immutable variables. Ruby doesn’t. (Yes, I know LISP isn’t purely functional. But it adheres to so many other FP paradigms that we can overlook that.)
But I’m getting distracted, so I’ll cut the above point short.
Anyway, what I wanted to say was this – just because your pet language has support for anonymous functions/closures doesn’t make it a functional language. Sure, Python has
In conclusion, don’t say your language is a functional one just because you borrowed a few ideas from Lisp. If you want a real functional language, try OCaml, Haskell, ML, or Scheme. Calling imperative/OOP languages functional just makes the term meaningless.