Thomas Kehrenberg

Learning programming with Swift


Programming is about telling a machine very very precisely what you want it to do.
The program code you are writing are instructions that tell the computer what to do.
The computer is in a sense very stupid because it will not do "what you meant",
but only exactly what you said.
If you have a large program with millions of lines of code,
one error in one line can make the whole program useless.

However, it's important to note,
that you basically cannot write a correct program on the first ry; except if it's very short.
As a programmer you first write some code,
test it out, discover lots of errors and then fix them.
This cycle is repeated until the code is correct.
Don't be afraid to write wrong code at the beginning!
Everyone does!

The other thing to know about programming is that is basically impossible to do
without re-using other people's code.
Lots of programers publish their code in the form of so-called libraries
that you can use.
The typical (useful) program makes use of dozens if not hundreds of libraries that other people wrote.
The idea is basically that someone solves a general problem once
and then other people can use the solution.

First steps

Consider this code:

let a = 2

We stated that the variable a should have the value 2.

Let's do something with a:

let a = 2

This puts the value of a into the output of the program.
print is a function, which despite the name has little to do with printing.
The function print takes the argument that you give it
and evaluates it and puts it into the output of the program.

Now where does this function print come from?
Well, it is part of the so-called standard library of Swift.
The standard library was written by the creators of the Swift programming language.
It contains lots of functions that are useful to all kinds of programs.

Let's look at this code. What do you think is the output of the program?

let a = 2
let result = (+)(a, 4)

We have here used a function which has a very weird name, namely (+).
Later, it will become clear why this name is so weird, but we'll ignore it for now.
As you might be able to guess, this function takes two arguments and adds them together.
It is also in the standard library of Swift.
This is a very nice function that someone wrote, so we don't have to write it.
Programmers use this function all the time.

Let's write our own function using (+).
Don't worry if you don't understand what's going on!
I will explain everything.

func addAndDouble(x: Int, y: Int) -> Int {
    let sum = (+)(x, y)
    let doubleSum = (+)(sum, sum)
    return doubleSum

let a = 2
let result = addAndDouble(x: a, y: 4)

There are lots of things going on here.
Let's look at them one by one.

First we have the word func.
Like the word let, this is a keyword.
It is a word that has a special meaning in Swift
and you cannot use that word as the name of a variable.

let func = 2

will give you an error and the program will not even run; let alone do what you want.

Now, while the keyword let is used to defining a new variable,
func is used to define a new function.
Following func is the function name.
In this case it's "addAndDouble".
In the parantheses are then the function arguments.
Let's ignore the business with the Ints for now:

func addAndDouble(x, y) {
    let sum = (+)(x, y)
    let doubleSum = (+)(sum, sum)
    return doubleSum

(this code won't work, but is illustrative)

Our function has two arguments (or "inputs") which we named x and y.
Arguments are kind of like variables.
We can give them any name we want (except names that are keywords).

Within the curly braces ({...}) we have the function body.
This is where we define what the function is supposed to do.
In this case we define a new variable called sum
which is equal to the sum of x and y.
Then we define another variable called doubleSum
which is equal to two times the value of sum.
This "double sum" is supposed to be the output of the function.
Thus, we use the keyword return to declare
that the value of doubleSum is the output of our function addAndDouble(x, y).
The keyword return is usually used at the end of the function body,
but there are also some special cases where it's useful to use it in other places.

Now let's add back the Ints. What are they about?

func addAndDouble(x: Int, y: Int) -> Int {
    let sum = (+)(x, y)
    let doubleSum = (+)(sum, sum)
    return doubleSum

Int specifies a type.
What is a type?
The type tells you what type of data a variable holds.
In our case, the variables hold numbers.
More specifically, whole numbers, which are integers.
And that's what the type Int refers to: integers.
x: Int simply tells the computer that x is supposed to be an integer.
And the -> Int means that the output of the function is also an integer.

Now, why do we have to specify the type of x and y?
Well, what we intend to do with x and y is add them together.
And you can only do that with numbers!
So, in order for our function to work, x and y have to be numbers.
That's why we're specifying the type Int.
Another function might take other types as inputs.

What other types of data are there?
The most basic ones are: Int, Double, String and Bool.
All the other data types are basically combinations of these.
Let's go through them.


This type is for floating point numbers which refers to numbers like 3.2 or 0.003.
So, not whole numbers.
Our addAndDouble(x, y) function could also have accepted Doubles as arguments.
We can define a variable with a Double value like so:

let pi: Double = 3.14

But you might ask: why is this type called "Double"?
The name "Double" is short for "double precision floating point".
There are also single precision floating point, but we will ignore them for now.
Most languages treat floating point numbers by default as double precision,
so it is easier to work with Double.
I'm truly sorry about the confusing name, but that's just how this type is called in nearly every language.

As you would expect, you can use the (+) function with variables of this type:

let pi: Double = 3.14
let doublePi = (+)(pi, pi)

Now, you might wonder: if we have Double, why do we need Int?
After all, Int is a subset of Double.
The answer is that it is often useful to restrict an argument to Int.
But there are in fact programming languages that don't have Ints; only Doubles.


This is the type for text.
Why is this type called String and not, for example, Text or Letters?
It comes from "string of characters" and was defined in the 1960s.
It's not the greatest name, but basically all programming languages use it.

When we define a string variable, we use quotation marks:

let greeting: String = "Hello, world!"

Of course, a string can also contain a random mix of letters and numbers:

let nonsense: String = "2d;l8dfh;348fhea"

It's important to note that, for example, 9 and "9" mean two very different things.
These two variables do not contain the same value:

let a: Int = 9
let b: String = "9"

The first one contains a number that can be used to do math.
The second one is a string that happens to have a number in it.
The computer stores these very differently.
This can be a bit confusing at the beginning.

A string is certainly something that our function add(x, y) cannot accept as an argument.
And if you try to do

let f = addAndDouble(x: "Hello", y: 2)

you will get an error.
Which is good, because it doesn't make any sense.


This type might be a bit weird at first, but it is very useful.
Variables that have type Bool can only have 1 of 2 values: true or false.
The names true and false are keywords that cannot be used for variable names.
So, we might write:

let nice_weather: Bool = true

The name of the type, Bool, comes from the mathematician George Boole.
The usefulness of this type will become clear when we have introduced if-statements.

In the previous code, we have written variable definitions like

let a = 2

without type specification.
This is possible because when we write it like that,
it's obvious what kind of data the variable a contains: a 2 which is an integer.
But we can also write it explicitly if we want to:

let a: Int = 2

In fact, if you want to define a Double variable with the value 2, you have to specify it:

let a: Double = 2

Alternatively, you can also write 2.0:

let a = 2.0

Then a has type Double.

Let's recap what we have learned.

func addAndDouble(x: Int, y: Int) -> Int {
    let sum = (+)(x, y)
    let doubleSum = (+)(sum, sum)
    return doubleSum

defines a function which takes two integers and gives one integer back,
which is two times the sum of the two inputs.

This code gives an error:

let greeting = "Hello"
let result = addAndDouble(x: greeting, y: 2)

because the variable greeting contains a string (i.e. text)
which is not a valid argument for the function add.

In our examples, we have made use of two functions from the standard library: print and (+).
There are of course many more.
Amongst them for example (-) for subtracting, (*) for multiplying and (/) for dividing numbers.

We have also already encountered the following keywords: let, func, return, true, false.
But there are a few more keywords to discover.

Lesson end
Next lesson: structs (use StructName.init() to initialize structs)

Warum schreibt man im Deutschen "ei", obwohl es eigentlich wie "ai" ausgesprochen wird?

Die kurze Antwort ist, dass sich die gesprochene Sprache gewandelt hat, während die geschriebene Sprache gleich geblieben ist. Im Mittelhochdeutschen wurde die Buchstabenkombination "ei" noch so ausgesprochen, wie man es erwarten würde (also ungefähr so wie das "ay" im Englischen "to say"), aber im Frühneuhochdeutsch hat sich die Aussprache dann geändert. Die Zeit des Frühneuhochdeutschen begann ungefähr im Jahr 1350, in manchen Gegenden ein bisschen später, und veränderte die Aussprache der deutschen Sprache in vielen Hinsichten. Eine wichtige Ausnahme dabei ist allerdings das Schweizerdeutsch (das richtige Schweizerdeutsch, welches ein Deutscher ohne Übung nicht verstehen kann), welches diesen Wechsel nicht mitgemacht hat. Im Schweizerdeutschen spricht man das geschriebene "ei" also noch so wie im Mittelhochdeutschen aus.

Die lange Antwort ist ein bisschen komplizierter. Um die Erklärung ein bisschen zu erleichtern, werde ich Anführungszeichen benutzen, wenn ich mich auf die geschriebene Sprache beziehe (z.B. "ei") und eckige Klammern benutzen, wenn ich mich auf Aussprache beziehe (z.B. [ei]). Ich sage dann zum Beispiel, dass "Heim" im Neuhochdeutschen [haim] ausgesprochen wird.

Was ist also die Komplikation, die ich erwähnt habe? Das Neuhochdeutsche "ei" ist eigentlich die Zusammenführung von zwei verschiedenen Vokal-Lauten: dem mittelhochdeutschen "ei" (gesprochen [ei]) und dem mittelhochdeutschen langen i. So stammt das neuhochdeutsche "Bein" vom mittelhochdeutschen "bein" (gesprochen [bein]), während das neuhochdeutsche "mein" von "miin" (mit einem langen i) abstammt. Den Wandel vom langen i zum [ai], kann man auch schön an dem Wort "frei" sehen. Im Holländischen wird das Wort "vrij" geschrieben, was noch stark an ein langes i erinnert, aber wird eher wie eine Mischung aus [frei] und [frai] ausgesprochen. Die Schriftsprache spiegelt also noch das lange i wider, während die Aussprache sich dem [ai] angenähert hat.

Meine Vermutung ist, dass das mittelhochdeutsche lange i zunächst mit dem mittelhochdeutschen [ei] verschmolzen ist, und daraufhin die Schreibweise angepasst wurde: "miin" zu "mein" und so weiter. Im zweiten Schritt ist dann der vereinte Laut zu [ai] geworden; ohne dass die Schreibweise angepasst wurde. Ich habe zu dieser Vermutung allerdings keine direkte Quelle gefunden.

An dieser Stelle kann man sich allerdings fragen: wenn das lange i zu [ai] geworden ist, wieso gibt es dann noch immer ein langes i im Neuhochdeutschen? (Zum Beispiel in "Liebe".) Die Antwort ist, dass ein anderer Laut des Mittelhochdeutschen auf den Platz des langen i gerutscht ist: der Diphtong "ie". Das "ie", welches wir im Neuhochdeutschen [ii] aussprechen, wurde im Mittelhochdeutschen tatsächlich [ie] gesprochen (also ungefähr so wie in "siehe" aber ohne das h). Das ist also die historische Erklärung dafür, dass wir im Hochdeutschen oft "ie" für das lange i schreiben.

Die letzte Frage ist, wieso hat sich die Aussprache in dieser Weise geändert? Das ist keine leichte Frage. Zunächst muss allerdings klargestellt werden, dass solche Lautverschiebungen sehr häufig passieren. Das Englische hat (unabhängig?) genau die gleiche Lautverschiebung vollzogen, in der das lange i zu [ai] wurde. Das Wort für "ich", "I", wird [ai] ausgesprochen, aber mit einem i geschrieben. (Als Nebenbemerkung, das heutige lange i in Wörtern wie "free" wurde im Englischen zwischenzeitlich tatsächlich wie [free] (mit langem e) ausgesprochen, aber dieser Laut hat sich verschoben und ist zum langen i geworden.) Der große Unterschied zum Deutschen ist, dass die englische Schriftsprache so gut wie gar nicht an die neue Aussprache angepasst wurde.

Für mich klingt folgendes plausibel als Grund für den Wandel: zunächst fingen die Bewohner im deutschen Sprachraum an, [ei] und [ii] zusammenzulegen. Mittelhochdeutsch hatte vielleicht einfach zu viele Laute, so dass es kein Problem war, einen Laut weniger zu haben. Das zusammengelegte [ei] und das existierende [ie] klangen dann vielleicht einfach zu ähnlich, so dass sich diese beiden Laute dann voneinander wegbewegt haben. Das [ei] in Richtung [ai] und das [ie] in Richtung [ii].