Take the 2-minute tour ×
Programmers Stack Exchange is a question and answer site for professional programmers interested in conceptual questions about software development. It's 100% free, no registration required.

Having looked at some languages for functional programming, I always wondered why some fp-languages use one or more whitespace characters for function application (and definition), whereas most (all?) imperative/object-oriented languages are using parentheses, which seems to be the more mathematical way. I also think that the latter style is much more clear and readable than without the parens.

So if we have a function f(x) = x² there are the two alternatives to calling it:

  • FP: f x

    Examples:

    • ML, Ocaml, F#
    • Haskell
    • LISP, Scheme (somehow)
  • Non-FP: f(x)

    Examples:

    • Almost all imperative languages (I know, see the comments/answers)
    • Erlang
    • Scala (also allows "operator notation" for single arguments)

What are the reasons for "leaving out" the parentheses?

share|improve this question
7  
To make it more confusing, erm, I meant succinct. –  Den Jul 8 at 7:53
7  
@Den if you learn haskell, the syntax will be one of the least confusing things :p –  Simon Jul 8 at 9:49
4  
You do realize the irony of saying that using parentheses would be more mathematical and then using the exponentiation function as an example? –  Jörg W Mittag Jul 8 at 10:43
11  
@Den you are doing yourself harm by rejecting a language because of its syntax. Surely you had no trouble learning xml or sql (those are not general purpose languages, but they define their own syntax). –  Simon Jul 8 at 11:08
5  
I would like to point out that shell scripts (e.g. bash) generally don't use parameters to call commands. PowerShell sort of has the worst of both worlds in that functions are declared with parentheses and called without them. –  Kris Harper Jul 8 at 14:30

5 Answers 5

up vote 49 down vote accepted

which seems to be the more mathematical way

functional languages are inspired by lambda calculus. In this field, parentheses are not used for function application.

I also think that the latter style is much more clear and readable than without the parens.

Readability is in the eye of the beholder. You are not used to reading it. It is a bit like mathematical operators. If you understand the associativity, you only need a few parens to clarify the structure of your expression. Often you don't need them.

Currying is also a good reason to use this convention. In haskell, you can define the following:

add :: Int -> Int -> Int
add x y = x + y

x = add 5 6 -- x == 11
f = add 5
y = f 6 -- y == 11
z = ((add 5) 6) -- explicit parentheses; z == 11

With parens, you could use two convention: f(5, 6) (not curried) or f(5)(6) (curried). The haskell syntax helps to get used to the currying concept. You can still use a non-curried version, but it is more painful to use it with combinators

add' :: (Int, Int) -> Int
add' (x, y) = x + y
u = add'(5, 6) -- just like other languages
l = [1, 2, 3]
l1 = map (add 5) l -- [6, 7, 8]
l2 = map (\x -> add'(5, x)) l -- like other languages

Notice how the second version forces you to register x as a variable, and that the subexpression is a function which takes an integer and adds 5 to it? The curried version is much lighter, but also considered by many as more readable.

Haskell programs makes extensive use of partial application and combinators as a mean of defining and composing abstractions, so this is not a toy example. A good function interface will be one where the order of parameters provides a friendly curried usage.

Another point: a function without parameters should be called with f(). In haskell, since you only manipulate immutable lazy evaluated values, you just write f, and consider it as a value which will need to perform some computations when needed. Since its evaluation won't have any side effect, it makes no sense to have a different notation for the parameterless function and its returned value.

There are also other conventions for function application:

  • Lisp: (f x) -- prefix with external parentheses
  • Forth: x f -- postfix
share|improve this answer
7  
Minor nitpick: the terms are "currying" and "curried", not "currification" and "currified". –  Doval Jul 8 at 11:22
    
"non curried" what's a non-curried function in haskell ? –  user1737909 Jul 9 at 11:09
3  
@user1737909 A function that takes a tuple as an argument. –  Doval Jul 9 at 12:02
1  
@Doval Actually it should be “schönfinkeling” and “schönfinkeled”. But oh well, history always defines the winner retrospectively. –  Profpatsch Sep 14 at 15:28

The basic idea is to make the most important operation (function application) easiest to read and easiest to write. A space is very unintrusive to read and very easy to type.

Note that this is not specific to functional languages, e.g. in Smalltalk, one of the first OO languages and languages inspired by it (Self, Newspeak, Objective-C), but also in Io and languages inspired by it (Ioke, Seph), whitespace is used for method calls.

Smalltalk-style:

anArray sort
anArray add: 2
aString replace: "a" with: "b"

(In the latter case, the name of the method is replace:with:.)

Io-style:

anArray sort
anArray add(2)
aString replace("a", "b")

Scala also allows whitespace for method calls:

foo bar(baz)

And leaving off the parentheses if there is only one argument:

foo bar baz

Ruby also allows you to leave off the parentheses:

an_array.sort
an_array.add 2
a_string.replace "a", "b"

using parentheses, which seems to be the more mathematical way

Not really:

f(x)
sin x
x²
|x|
x!
x + y
xy
½

Math notation has evolved over a long time in a horribly inconsistent way.

If at all, functional languages take their inspiration from λ-calculus where function application is written using whitespace.

share|improve this answer
3  
There is also an argument for economy of editing. In particular, functional languages typically support composition directly. Putting parentheses around the function instead of the argument makes sense. You only have to do it "once": (e . f . g) x as opposed to e(f(g(x))). Also, Haskell, at least, would not stop one from doing f(x) instead of f x. It's just not idiomatic. –  nomen Jul 8 at 22:34

Parenthesis for function application is just one of the many saddles Euler left us with. Like anything else mathematics needs conventions when there are several ways to do something. If your mathematical education only extends as far as a non-maths subject at university then you probably aren't too familiar with the many fields where function application happens happily without any of these nonsense brackets (e.g. Differential Geometry, Abstract Algebra). And you don't even mention functions that are applied infix (almost all languages), "outfix" like taking a norm, or diagrammatically (Befunge, Algebraic Topology).

So in answer I'd say it's due to a much higher proportion of functional programmers and language designers having extensive mathematical education. Von Neumann says "Young man, in mathematics you don't understand things. You just get used to them.", certainly this is true of notation.

share|improve this answer
7  
Don't even get me started on f(x) vs. sin x vs. vs. |x| vs. x! vs. x + y vs. xy vs. ½ vs. a summation vs. an integral vs. … –  Jörg W Mittag Jul 8 at 15:28
2  
+1 for the von Neuman quote. +1 for the rest of the answer, but I can't give +2. :( –  pvorb Jul 9 at 0:17
2  
I catch a hint of elitism here; I dispute the neutrality of "functional programming language designers are better educated". –  CaptainCodeman Jul 9 at 6:59
4  
@CaptainCodeman He says more educated in mathematics, a statement with which I agree. At least when it comes to Haskell, you can notice that both the concepts are more mathematical in nature and the community is more mathematically inclined as well. They're not more intelligent, just better educated in mathematics. –  Paul Jul 9 at 11:18
2  
@CaptainCodeman No, since he never implied they are more educated in general, just more educated in mathematics. That's exactly what he said: "extensive mathematical education". :) –  Paul Jul 9 at 11:38

Although there's a lot of truth in Simon's answer, I think there's also a much more practical reason. The nature of functional programming tends to generate a lot more parentheses than imperative programming, due to function chaining and composition. Those patterns of chaining and composition also usually happen to be able to be unambiguously represented without parentheses.

The bottom line is, all those parentheses get annoying to read and track. It's probably the number one reason LISP isn't more popular. So if you can get the power of functional programming without the annoyance of excess parentheses, I think language designers are going to tend to go that way. After all, language designers are also language users.

Even Scala allows the programmer to omit parentheses in certain circumstances, which happen to come up fairly frequently when programming in a functional style, so you sort of get the best of both worlds. For example:

val message = line split "," map (_.toByte)

The parens at the end are necessary for associativity, and the others are left off (as well as the dots). Writing it this way emphasizes the chained nature of the operations you're performing. It might not be familiar to an imperative programmer, but to a functional programmer it feels very natural and flowing to write this way, without having to stop and insert syntax that adds no meaning to the program, but is just there to make the compiler happy.

share|improve this answer
1  
"The bottom line is, all those parentheses get annoying to read and track. It's probably the number one reason LISP isn't more popular.": I do not think parentheses are a reason for Lisp not to be popular: I do not think they are particularly difficult to read, and I find other languages have a much more awkward syntax. –  Giorgio Jul 8 at 16:57
1  
LISP syntax largely makes up for the annoying parentheses with its super-high degree of orthogonality. That just means it has other redeeming features that make it still usable, not that the parens aren't annoying. I understand not everyone feels that way, but the vast majority of programmers I've met do. –  Karl Bielefeldt Jul 8 at 17:08

Both premises are wrong.

  • These functional languages don't use space for function application. What they do is simply parse any expression that comes after a function as an argument.

    GHCi> f 3
    4
    GHCi> f(3)
    4
    GHCi> (f)3
    4

    course if you use neither a space nor parens then it normally won't work, simply because the expression isn't properly tokenised

    GHCi> f3

    <‌interactive>:7:1:
        Not in scope: ‘f3’
        Perhaps you meant ‘f’ (line 2)

    But if these languages were restricted to 1-character variable names then it would work too.

  • Nor do mathematics conventions normally require parentheses for function application. Not only will mathematicians often write sin x – for linear functions (usually called linear operators then) it's also very much usual to write the argument without parens, perhaps because (much like any function in functional programming) linear functions are often handled without directly supplying an argument.

So really, your question boils down to: why to some languages require parentheses for function application? Well, apparently some people, like you, consider this more readable. I strongly disagree with that: one pair of parens is nice, but as soon as you have more of two of them nested it starts to get confusing. Lisp code demonstrates this best, and pretty much all functional languages would look similarly cluttered if you needed parens everywhere. This doesn't happen so much in imperative languages, but mainly because these languages aren't expressive enough to write concise, clear one-liners in the first place.

share|improve this answer
    
Got me, the question is not perfect. :) So the conclusion to draw is: "Parentheses don't scale." –  pvorb Jul 9 at 0:13
2  
Nor are non-functional languages that unanimous in requiring parentheses; for a few examples, Smalltalk has object method: args, Objective C has [object method: args], and Ruby and Perl both allow omitting parentheses in function and method calls, only requiring them to resolve ambiguity. –  hobbs Jul 9 at 5:39

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.