The problem: repeated code
Suppose a teacher asks a student to write the same three lines on the whiteboard three times. As a program, the direct version repeats every line:
console.log("This is Andy");
console.log("Andy made a mistake");
console.log("Andy suffers the consequences");
console.log("This is Andy");
console.log("Andy made a mistake");
console.log("Andy suffers the consequences");
console.log("This is Andy");
console.log("Andy made a mistake");
console.log("Andy suffers the consequences");
Nine lines for three repetitions is manageable. But ask for 100 repetitions, or for ten lines of text instead of three, and the file becomes huge. Worse, every change has to be made in every copy. If the name must change, you edit each copy, and missing one leaves a program that disagrees with itself.
The solution: a function
A function is a named block of code that you write once and run whenever you want. In TypeScript you define it with the function keyword, a name, parentheses and a body in braces:
function printMessage(): void {
console.log("This is Andy");
console.log("Andy made a mistake");
console.log("Andy suffers the consequences");
}
printMessage();
printMessage();
printMessage();
The three calls print the same nine lines as before. The code that does the work now exists in one place.
Two ideas matter here:
- Defining is not running. The definition only teaches the program what
printMessagemeans. The body runs each time you call the function by writing its name followed by parentheses. - Calling repeats the body. Each call runs the whole body from the start. Three calls give three runs.
The return type void
The : void after the parentheses is a TypeScript annotation. It says the function does not return a useful value; it only has an effect, here printing. The annotation helps the compiler catch mistakes, but it is erased when the code is compiled to JavaScript, so it changes nothing at run time. You can leave it out and TypeScript works out the type itself, but writing it makes the intent clear.
Changing the story
With the function, changes are cheap. To print the text twice more, add two calls instead of six lines. To change the student from Andy to Mike, edit the three lines inside the function, and every call picks up the change:
function printMessage(): void {
console.log("This is Mike");
console.log("Mike made a mistake");
console.log("Mike suffers the consequences");
}
printMessage();
printMessage();
printMessage();
printMessage();
printMessage();
The repeated printMessage(); lines are still a little awkward. Loops, which come later, remove that repetition too.
The lesson's exercise
The exercise gives you a starter file with three comments and one line already written:
// Function goes here:
// Introduce yourself the first time:
console.log("Sorry, I didn't hear you");
// Introduce yourself again:
You build the program in five steps:
- Define the function. Under the first comment, write
function introduceYourself(): void { }. At this point, nothing runs. - Print the first line. Inside the braces, print
"My name is Andy"withconsole.log. - Print the second line. On the next line, still inside the braces, print
"I code in Python". - Call it the first time. Under the second comment, write
introduceYourself();. The semicolon ends the statement. Both lines are printed here. - Call it again. Under the last comment, which is after the
"Sorry, I didn't hear you"line, write the same call. Both lines are printed again without being typed again.
The finished program:
// Function goes here:
function introduceYourself(): void {
console.log("My name is Andy");
console.log("I code in Python");
}
// Introduce yourself the first time:
introduceYourself();
console.log("Sorry, I didn't hear you");
// Introduce yourself again:
introduceYourself();
Its output is:
My name is Andy
I code in Python
Sorry, I didn't hear you
My name is Andy
I code in Python
Common mistakes
- Defining the function but never calling it. The program then prints only the "Sorry" line.
- Leaving out the parentheses in the call. Writing
introduceYourself;only mentions the function. It does not run it. - Putting a print outside the braces. A line after the closing brace is not part of the function and runs on its own, once, at that point in the file.
- Misspelling the name. Names are case-sensitive, so
introduceyourself()is notintroduceYourself(), and the compiler reports that it cannot find the name.
Key takeaways
- A function names a block of code so you can write it once and run it many times.
- Defining a function does not run it; a call, with parentheses, does.
- Changing the function body changes the behaviour of every call.
- The
voidreturn type marks a function that only performs an action.