Luet oppimateriaalin englanninkielistä versiota. Mainitsit kuitenkin taustakyselyssä
osaavasi suomea. Siksi suosittelemme, että käytät suomenkielistä versiota, joka on
testatumpi ja hieman laajempi ja muutenkin mukava.
Suomenkielinen materiaali kyllä esittelee englanninkielisetkin termit.
Kieli vaihtuu A+:n sivujen yläreunan painikkeesta. Tai tästä: Vaihda suomeksi.
About This Page
Questions Answered: What would make higher-order functions easier
to work with? How can I define a function “on the fly” as I use it?
Topics: Function literals and anonymous functions. Scala’s
shorthand notations for function literals.
What Will I Do? Read and work on small assignments.
Rough Estimate of Workload:? Two hours or so.
Points Available: A35 + B5 + C5.
Related Modules: HigherOrder. We’ll touch on AuctionHouse1, too.
In this chapter, you won’t learn to create new sorts of programs. What you will learn
is new ways of writing functions. These new notations aren’t a theoretical exercise but
will help you program more efficiently.
But let’s not go there just yet. Let’s start with numbers.
Already in Week 1, you learned to store numbers in variables. You can use a variable
name to refer to a number, which is convenient especially when you need to refer to
the same number in multiple places within your program.
On the other hand, we don’t always use variable names to refer to numbers. If we have
a var named index and wish to increment its value by one within a loop, we typically
won’t write this:
val incrementSize = 1
index += incrementSize
Instead, we’ll probably use the integer literal 1 simply to write index += 1. As
you know, a literal is an expression that expresses a specific value “directly” or
“literally” as written in code. There are many reasons to use a literal in index += 1:
index += 1
A human reader can easily make sense of “incrementing by one” as a
The purpose of 1 in index += 1 is readily apparent from the
command, so introducing an additional variable and its name
incrementSize doesn’t really make the program any more readable.
incrementSize is (presumably) a single-shot variable that isn’t
used anywhere else in the program.
If we don’t have incrementSize, readers of our program code don’t
have to consider whether the variable might have some broader meaning
in the program apart from its use in index += incrementSize.
index += incrementSize
Given all of the above, index += 1 is a shorter way to express
the same thing without being harder to read. (In fact, it may be
Enough about numbers. How is this relevant to functions?
Since Week 1, you have used def to define functions that have names. You have used the
functions’ names to refer to particular operations much like you have used variables’
names to refer to particular numbers. Function names are especially convenient when you
want to call the same function multiple times, perhaps from different parts of the program.
In this chapter, you’ll see that you can also define anonymous, “single-shot” functions.
For that, we need function literals.
In Chapter 6.1 we discussed the following example function, which calls its parameter
def twice(operation: Int => Int, target: Int) = operation(operation(target))
We used this function to twice add one to a number, and to twice double a number. So we
defined and named these two mini-functions:
def next(number: Int) = number + 1
def doubled(original: Int) = 2 * original
Here’s how we used twice in Chapter 6.1:
twice(next, 1000)res0: Int = 1002
twice(doubled, 1000)res1: Int = 4000
There is an easier way to accomplish the same thing. Let’s suppose we’ve defined twice
as above. However, we’ll now discard next and doubled; we won’t need them if we define
functions “on the fly” as we pass them to twice.
twice(number => number + 1, 1000)res2: Int = 1002
We use a function literal (funktioliteraali) that defines
an anonymous function (nimetön funktio). You can read this
literal as “an anonymous function that takes in a parameter number
and returns the value number + 1”. This anonymous function is
passed to twice as its first parameter and consequently invoked
number + 1
A rightward arrow indicates that this is a function literal. The
parameters of the anonymous function are listed on the left (here,
we have only one) and body of the function is written on the right
(here, it’s a simple sum).
We can similarly use a function literal to double a number twice:
twice(n => 2 * n, 1000)res3: Int = 4000
The function literal defines an anonymous function that returns
a value twice as big as its input.
We could have written original or some other name in place of
n, here. Where it doesn’t cause confusion, it’s common to use
simple names for the parameters of function literals in order to
keep the literal short and crisp.
The arrow: function literals contain the same sort of arrow that you already know
from function types (e.g., the Int => Int in the definition of twice).
Int => Int
Parameter types in a literal: you can often omit the parameter types of a function
literal because Scala can work out the types from the context. For instance, in our
example above, we didn’t have to explicitly tell the computer the type of number in
number => number + 1. Given that we passed that function literal to twice, which
expects a function of type Int => Int, it can be inferred that number is an Int.
number => number + 1
As said, parameter types can very often be automatically inferred. When that isn’t the
case, you can explicitly mark down the types just like you’ve done with named functions:
use round brackets and colons. For example, you can write the literal number => number + 1
in full as (number: Int) => number + 1.
(number: Int) => number + 1
Brackets: when a function literal takes only a single parameter whose type can be
inferred, you can omit the round brackets that usually surround parameter lists. Which
is what we did in our examples above. If you have multiple parameters, you must write the
brackets. (See below for examples.) It’s never wrong to write the brackets.
Let’s use the REPL to examine how function literals turn into anonymous function objects.
Here’s an increment-by-one literal:
(number: Int) => number + 1res4: Int => Int = <function1>
The REPL confirms: we have a value of type Int => Int.
Here, we actually needed an explicit type annotation for
number, because there is no context to indicate its type.
(For all Scala knows, we might have intended for number
to be a Double or a String, for instance.)
The literal below defines a function that takes two parameters, divides one by the other,
and returns a rounded result. It has the type (Double, Double) => Int.
(Double, Double) => Int
(x: Double, y: Double) => (x / y).round.toIntres5: (Double, Double) => Int = <function2>
A function defined by a function literal is an object. You can use it like you use other
The function itself has no name. However, we can make a variable refer to an anonymous
val myFunc = (x: Double, y: Double) => (x / y).round.toIntmyFunc: (Double, Double) => Int = <function2>
Now we can use the variable’s name to call the function:
myFunc(10, 4)res6: Int = 3
It’s also perfectly possible to have another variable refer to the same function:
val roundedDivision = myFuncroundedDivision: (Double, Double) => Int = <function2>
Now this works too:
roundedDivision(100, 8)res7: Int = 13
Functions as objects
In Chapter 5.3, you saw that if a Scala object has a method named
apply, it serves as a sort of “default method” for that object. For
instance, the expression myObject(params) is simply a shorthand
notation for the method call myObject.apply(params). In effect, you
can use an object with an apply method “as if it was a function”.
All of Scala’s function object have an apply method, and the
following command means precisely the same as the one above.
roundedDivision.apply(100, 8)res8: Int = 13
From an object-oriented point of view, to call a function is to call
its apply method.
The strengths and weaknesses of function literals are similar to those of, say,
integer literals. Here are some of the strengths:
You don’t need to define names for every last tiny function that
you use only once.
You can write the function literal precisely where you need the
function. For example, you can write a literal within a twice
call so that your anonymous function is affixed to what you do
with it. This can make your code more readable, especially if the
function literal is short.
Function literals can generally make your code shorter.
Brevity is not an end in itself, but it’s a nice bonus unless
it results in cryptic code.
Limitations and weaknesses:
Anonymous function have no names. Sometimes, the lack of names
makes code harder to read.
Writing and reading function literals can be a challenge at
first (but it soon gets easier with practice).
There are many functions that need a name, such as the public
methods on objects. Anonymous functions don’t work for all needs.
If we wish to call an anonymous function multiple times, we
need a variable (a name) that we can use to refer to the function.
Anonymous functions need to be used with care. One excellent use is to pass short
anonymous functions as parameters to other functions, as we did above.
Anonymous functions are very common; using them is a skill that pays off to learn. In O1,
we’ll be using anonymous functions extensively.
Terminological note: lambda
You may hear function literals referred to as lambda expressions
and anonymous functions referred to as lambda functions. Some
programming languages also use “lambda” as a keyword; in the Python
language, for instance, the expression lambda number: number + 1
corresponds to Scala’s number => number + 1.
lambda number: number + 1
That convention has its own history. This sort of expressions originate
in the lambda calculus
of the mathematician Alonzo Church, who had a pivotal role in the
development of computer science.
As for how the Greek letter lambda ended up naming that branch of
mathematics, that happened almost literally by pulling the name from a
hat: Church didn’t write number => number + 1 but ŷ.y+1, that is,
he used a so-called hat
on top of the parameter. However, the typesetters of the 1930s apparently
had trouble with that and yanked the hat a bit to the left, producing
^y.y+1 where it looked like Λ, a lambda.
Many of the examples from Chapter 6.1 can be expressed elegantly with function literals.
Let’s rewrite some of them.
Here is how we used tabulate to initialize a vector:
Vector.tabulate(10)(doubled)res9: Vector[Int] = Vector(0, 2, 4, 6, 8, 10, 12, 14, 16, 18)
We don’t need doubled for that. We can do the same thing neatly with an anonymous
Vector.tabulate(10)(index => 2 * index)
A+ presents the exercise submission form here.
An effortless way to make your code a little bit easier to read is
to put space characters around function literals so that they
stand out better from their context.
Vector.tabulate(10)( index => 2 * index )
In this ebook, we’ll frequently do this. You may also wish to adopt this convention.
In Chapter 6.1, we wrote this higher-order function:
def areSorted(first: String, second: String, third: String, compare: (String, String) => Int) =
compare(first, second) <= 0 && compare(second, third) <= 0
We also defined these functions that work as parameters for areSorted:
def compareLengths(string1: String, string2: String) = string1.length - string2.length
def compareIntContents(string1: String, string2: String) = string1.toInt - string2.toInt
def compareChars(string1: String, string2: String) = string1.compareToIgnoreCase(string2)
We used them like this:
areSorted("Java", "Scala", "Haskell", compareLengths)
areSorted("Java", "Scala", "Haskell", compareChars)
areSorted("200", "123", "1000", compareIntContents)
Now that we know about function literals, we can rewrite the three expressions above as:
areSorted("Java", "Scala", "Haskell", (s1, s2) => s1.length - s2.length )
areSorted("Java", "Scala", "Haskell", (s1, s2) => s1.compareToIgnoreCase(s2) )
areSorted("200", "123", "1000", (s1, s2) => s1.toInt - s2.toInt )
Don’t forget the brackets.
In Chapter 6.1, we added a findAll method to class AuctionHouse. It’s given a function
that represents a search criterion and finds all items that match that criterion.
class AuctionHouse(val name: String):
private val items = Buffer[EnglishAuction]()
def findAll(checkCriterion: EnglishAuction => Boolean) =
val found = Buffer[EnglishAuction]()
for currentItem <- this.items do
if checkCriterion(currentItem) then
found += currentItem
This is how we used findAll:
def checkIfOpen(candidate: EnglishAuction) = candidate.isOpen
def checkIfHandbag(candidate: EnglishAuction) = candidate.description.toLowerCase.contains("handbag")
def findAll(checkCriterion: EnglishAuction => Boolean) =
val house = AuctionHouse("ReBay")
house.addItem(EnglishAuction("A glorious handbag", 100, 14))
house.addItem(EnglishAuction("Collectible Easter Bunny China Thimble", 1, 10))
println(house.findAll(checkIfOpen)) // finds both auctions
println(house.findAll(checkIfHandbag)) // finds only the first auction
How would you implement testFindAll with anonymous functions instead? That is, let’s
assume that we don’t have the named functions checkIfOpen and checkIfHandbag. How
would you rewrite the two last commands that call findAll?
Some more old code from 6.1:
def blueGradient(x: Int, y: Int) = Color(0, 0, x.toDouble / (size - 1) * Color.Max)blueGradient(x: Int, y: Int): Color
Pic.generate(size, size, blueGradient)res10: Pic = generated pic
We can replace the above with this:
Pic.generate(size, size, (x, y) => Color(0, 0, x.toDouble / (size - 1) * Color.Max) ) res4: Pic = generated pic
How about this Pic-generating example?
def artwork(x: Int, y: Int) =
if x * x > y * 100 then Red
else if x + y < 200 then Black
else if y % 10 < 5 then Blue
else Whiteartwork(x: Int, y: Int): Color
Pic.generate(size, size * 2, artwork)res11: Pic = generated pic
The longer your function literal would be, the less likely it is to
improve readability. The following literal, for instance, is fairly
convoluted. Splitting it across multiple lines helps somewhat, but
we’re getting into territory where it would probably be better to
use a named function instead.
Pic.generate(size, size * 2, (x, y) => if x * x > y * 100 then Red else if x + y < 200 then Black else if y % 10 < 5 then Blue else White )res12: Pic = generated pic
A turning point in this chapter
Now you know how to use function literals to define
anonymous functions. Many but not all programming
languages support anonymous functions in one way or
another. Anonymous functions are used especially often in
the functional programming paradigm,
which we’ll say more about in Chapter 11.2.
The second half of this chapter is rather specific
to Scala: you will learn another notation for writing
When writing a short function literal, the name of the parameter variable often isn’t
too important. No matter which of the following you write, it will be obvious to the
reader that you’re defining a function that returns an incremented number.
number => number + 1
x => x + 1
something => something + 1
For that reason, Scala lets you leave out the parameter name altogether and so write
function literals very compactly.
Consider again the literal number => number + 1, whose core meaning is that 1
gets added to some given value. We can write a literal that captures just that core
meaning. This tiny expression defines exactly the same anonymous function:
_ + 1
The underscore means an anonymous parameter. Since our literal contains only a single
underscore, it defines a function that takes only a single parameter. One is added to
that parameter’s value; the sum is this anonymous function’s return value.
As you see, this abbreviated notation doesn’t feature a right-pointing arrow at all. The
underscore is enough to turn the expression into a function literal.
You can use these compact literals just like the full literals:
twice( _ + 1 , 1000) // returns 1002
twice( 2 * _ , 1000) // returns 4000
Earlier in this chapter, we listed some of the pros and cons of function literals
compared to named functions. Both the pros and the cons are further emphsized in
the compact “underscore literals”. If you use them judiciously, they are elegant
and improve readability. At first, they may seem nearly magical, but you’ll quickly
get used to them.
Annotating parameter types
You can usually leave out parameter types from abbreviated function
literals just like you can usually leave them out from the full
notation. We have done so in all the examples above.
You can add type annotations to abbreviated literals, too.
For instance, you could write _ + 1 as (_: Int) + 1. However,
anonymous parameters with type annotations usually aren’t the
nicest to read, and we won’t be doing this in O1.
_ + 1
(_: Int) + 1
A function can have multiple anonymous parameters: the first underscore in the function
literal refers to the first parameter, the second underscore to the second parameter, and
These two commands, for example, are equivalent:
Vector.tabulate(3, 5)( (row, column) => row + column )
Vector.tabulate(3, 5)( _ + _ )
You can similarly write these familiar function literals:
in a shorter form:
areSorted("Java", "Scala", "Haskell", _.length - _.length )
areSorted("Java", "Scala", "Haskell", _.compareToIgnoreCase(_) )
areSorted("200", "123", "1000", _.toInt - _.toInt )
Let’s say we have a collection of elements and we wish to print out each element in it.
Here are three instructions to that end, expressed in English:
Long form: “Repeat for each element: print x, where x is the
element being processed.”
Short form: “Repeat for each element: print the element.”
Very terse form: “Repeat for each element: print.”
In English, we can choose how we express ourselves based on what suits the context and
how we prefer to speak or write.
Scala is pretty flexible for a programming language. Like English, it lets you express
this meaning in different ways. Assuming that we’ve defined repeatForEachElement as in
Chapter 6.1, and a vector of integers, all of the following do the same thing:
Long form: repeatForEachElement(myVector, x => println(x) )
repeatForEachElement(myVector, x => println(x) )
Short form: repeatForEachElement(myVector, println(_) )
repeatForEachElement(myVector, println(_) )
Very terse form: repeatForEachElement(myVector, println)
The latter two are essentially shorthand for the longest version.
Consider another example. Let’s assume myObj refers to some object with an act
method that takes an Int parameter.
Long form: repeatForEachElement(myVector, element => myObj.act(element) )
repeatForEachElement(myVector, element => myObj.act(element) )
Short form: repeatForEachElement(myVector, myObj.act(_) )
repeatForEachElement(myVector, myObj.act(_) )
Very terse form: repeatForEachElement(myVector, myObj.act)
Given that all three work equally well, you can make the decision with readability in
mind. As with natural language, which one is best depends on the context and on the
reader. The very terse form says only what is required; it probably works best when the
parameter function is very familiar (like println is). In contrast, the “short form”
is more explicit about the fact that each of the values in turn becomes a parameter:
this is more apparent from myObj.act(_) than from myObj.act, which looks identical
to calling a parameterless method. The “long form” further highlights the parameter
variable and lets you name it.
You’ll see examples of all three forms in O1 and in Scala programs written by others.
It’s a good idea to know them all even if you prefer one of them yourself.
A rule of thumb
You can always use the long form of function literals — the one
with the arrow and the named parameters — until you feel like you’d
like a more succinct way to write things.
Abbreviated function literals have a limitation that is revealed by the following
Here is a function that uses its parameter to compute a result.
The key thing to note here is that the function body features
the same parameter more than once.
def compute(number: Double) = number * number + 10
We can express the same computation as an anonymous function:
number => number * number + 10
However, this abbreviated literal fails to do the same thing:
_ * _ + 10
Since each underscore corresponds to a separate anonymous parameter, the above literal
does the same as these functions:
(number1, number2) => number1 * number2 + 10
def compute(number1: Double, number2: Double) = number1 * number2 + 10
That is, the literal defines an entirely different function with two parameters.
You can use each anonymous parameter just once within the function literal: each
underscore refers to a separate parameter. If you need to refer to a function literal’s
parameter multiple times, use a full literal with named parameters.
Here is another example of the same restriction:
def swapGreenAndBlue(original: Color) = Color(original.red, original.blue, original.green)
The parameter variable original appears multiple times in
the function body. It’s possible to write a function literal that
corresponds to swapGreenAndBlue (and indeed you did so above),
but the parameter needs a name.
When you call another function within a function literal, you need to heed the following
restriction, which we’ll again explore through examples. These examples make use of the
doubled function that we defined earlier.
First, as a point of reference, consider these two expressions that we’ve already
discussed. Both increment 1000 twice to 1002:
Longer function literal
Do they work?
twice( x => x + 1 , 1000)
twice( _ + 1 , 1000)
Both work fine.
How about the next example? Here we’d like to do the following twice: add one and double
the result. Doing this on 1000 should produce 4006, for instance. So we write a function
literal that calls doubled:
twice( x => doubled(x + 1) , 1000)
twice( doubled(_ + 1) , 1000)
In this scenario, the compact literal doesn’t mean what we wanted. Instead, the underscore
“expands within the inner brackets”, so to speak. The literal doubled(_ + 1) stands for
doubled(x => x + 1), which isn’t a valid expression. In situations like this, use the
full literal notation.
doubled(_ + 1)
doubled(x => x + 1)
Below is a third example that does the following twice: first double the number, then add
one. Doing this on 1000 should produce 4003.
twice( x => doubled(x) + 1 , 1000)
twice( doubled(_) + 1 , 1000)
When there’s nothing at all except the underscore inside the brackets, as in doubled(_),
the underscore “expands outside the brackets”. Which is why the compact form works in this
These rules may well seem confusing at first. Don’t worry. You can always use the
lengthier literal notation.
The goal is to call a higher-order method like this:
myPic.transformColors( ??? )
Here’s a function literal that we could use where the question marks are:
pixel => pixel.lighter
May we rewrite this function literal using an anonymous parameter (an underscore)?
No, because the parameter is needed multiple times in the function body.
No, because a function call within the literal prevents it.
No, because you can’t use anonymous parameters when calling transformColors.
Pic.generate(256, 256, ??? )
(x, y) => Color(x, x, y)
May we similarly rewrite this function literal into abbreviated form?
No, because one of the parameters is needed multiple times in the function body.
No, because the parameters aren’t in a suitable order.
No, because you can’t use anonymous parameters when calling generate.
Vector.tabulate(5, 10)( ??? )
(row, column) => column - row * 2
May we rewrite this function literal as _ - _ * 2?
_ - _ * 2
No, because you can’t use anonymous parameters when calling tabulate.
Vector.tabulate(10)( ??? )
Here’s a function literal that we could use where the question marks are
(assuming Random has been imported):
index => Random.nextInt(10) + index
May we rewrite this function literal (as above)?
Yes. This works: Random.nextInt(10) + _
Random.nextInt(10) + _
upperLimit => Random.nextInt(1 + upperLimit)
Yes. This works: Random.nextInt(1 + _)
Random.nextInt(1 + _)
How about this expression?
number => 1 + Random.nextInt(number)
It does the same as this one: 1 + Random.nextInt(_)
1 + Random.nextInt(_)
1 + Random.nextInt(_) is invalid, because the parameter is in brackets.
turnElementsIntoResult(vectorOfInts, 0, ??? )
(count, nextElem) => count + (if nextElem < 0 then 1 else 0)
Yes. This works: _ + (if _ < 0 then 1 else 0)
_ + (if _ < 0 then 1 else 0)
No. The if around the second parameters causes that attempt to fail.
The goal is to call higher-order methods as shown:
val multiplicationTableFrom0 = Vector.tabulate(10, 10)( (row, column) => row * column )
val multiplicationTableFrom1 = Vector.tabulate(10, 10)( (row, column) => (row + 1) * (column + 1) )
We can rewrite the first of those lines like this:
val multiplicationTableFrom0 = Vector.tabulate(10, 10)( _ * _ )
Can we also rewrite the second line like this?
val multiplicationTableFrom1 = Vector.tabulate(10, 10)( (_ + 1) * (_ + 1) )
No. The attempt fails because the underscores appear within brackets and are part of an arithmetic expression.
Just as there are literal notations for strings, numbers, and the
like, there are literal notations for functions. A function literal
defines an anonymous function.
If you use them judiciously, anonymous functions can make your code
easier to write and easier to read.
Anonymous functions are particularly convenient when a short
function is needed in a single location only. A typical use case is
to call a higher-order function and pass in an anonymous function
constructed “on the fly”.
Scala has two notations for function literals. The full notation
uses a => arrow and names each parameter. The compact notation
uses underscores _ to indicate that not only the function, but
its parameters too, are anonymous.
The full notation always works. The abbreviated
notation works for many but not all purposes.
It’s fine to always use the full notation in your
own code, but you do need to be able to read both
Links to the glossary: function literal, anonymous function,
Please note that this section must be completed individually.
Even if you worked on this chapter with a pair, each of you should submit the form separately.
Time spent: (*) Required
Please estimate the total number of minutes you spent on this chapter (reading, assignments,
etc.). You don’t have to be exact, but if you can produce an estimate to within 15 minutes or
half an hour, that would be great.
“I feel that I have understood the most important things in this chapter.” (*) Required
I’m unable to answer or don’t want to comment.
Written comment or question:
You aren’t required to give written feedback. Nevertheless, please
do ask something, give feedback, or reflect on your learning!
(However, the right place to ask urgent questions about programs
that you’re currently working on isn’t this form but the lab sessions
or Piazza. We can’t guarantee that anyone will even see anything
you type here before the weekly deadline.)
Thousands of students have given feedback and so contributed to this ebook’s design.
The ebook’s chapters, programming assignments, and weekly bulletins have been written in
Finnish and translated into English by Juha Sorva.
The appendices (glossary, Scala reference,
FAQ, etc.) are by Juha Sorva unless otherwise specified on the page.
The automatic assessment of the assignments has been developed by: (in alphabetical order)
Riku Autio, Nikolas Drosdek, Joonatan Honkamaa, Antti Immonen, Jaakko Kantojärvi, Niklas
Kröger, Kalle Laitinen, Teemu Lehtinen, Jaakko Nakaza, Strasdosky Otewa, Timi Seppälä,
Teemu Sirkiä, Anna Valldeoriola Cardó, and Aleksi Vartiainen.
The illustrations at the top of each chapter, and the similar drawings elsewhere in the
ebook, are the work of Christina Lassheikki.
The animations that detail the execution Scala programs have been designed by Juha
Sorva and Teemu Sirkiä. Teemu Sirkiä and Riku Autio did the technical implementation,
relying on Teemu’s Jsvee and Kelmu toolkits.
The other diagrams and interactive presentations in the ebook are by Juha Sorva.
The O1Library software
has been developed by Aleksi Lukkarinen and Juha Sorva. Several of its key components
are built upon Aleksi’s SMCL
The pedagogy of using O1Library for simple graphical programming (such as Pic) is
inspired by the textbooks How to Design Programs by Flatt, Felleisen, Findler, and
Krishnamurthi and Picturing Programs by Stephen Bloch.
The course platform A+ was originally created at Aalto’s LeTech
research group as a student project. The open-source project
is now shepherded by the Computer Science department’s edu-tech team and hosted by the department’s IT
Markku Riekkinen is the current lead developer; dozens of Aalto students and others have also contributed.
The A+ Courses plugin,
which supports A+ and O1 in IntelliJ IDEA, is another open-source project. It has been designed and
implemented by various students
in collaboration with O1’s teachers.
For O1’s current teaching staff, please see Chapter 1.1.
Additional credits appear at the ends of some chapters.
We use a function literal (funktioliteraali) that defines an anonymous function (nimetön funktio). You can read this literal as “an anonymous function that takes in a parameter
numberand returns the value
number + 1”. This anonymous function is passed to
twiceas its first parameter and consequently invoked two times.