008 — The Function Type in TypeScript (params, defaults, void)
Full companion narrative for TypeScript Tutorial — The Function Type: inferred vs explicit function types, typed/optional/default parameters, return types, and void vs undefined
Video: 008 · TypeScript Tutorial - The Function Type in TypeScript · watch · 8:14 · Net Ninja TypeScript tutorial series
Source: this is a written companion to the video. Part of the Favorite TypeScript Videos curated path, module 04 (functions and generics). The first function lesson: how function types are inferred, how to declare them, and how parameters and return types are typed.
inferred function type
A variable initialized with a function is inferred to hold a function, the same way a variable initialized with a string or boolean is inferred as string/boolean. Reassigning it to a non-function afterwards is a type error.
let greet = () => {
console.log("hello, world");
};
// Error: Type 'string' is not assignable to type '() => void'
greet = "hello";
explicit Function type (capital F)
Instead of initializing immediately, a variable can be declared ahead of time as holding some function, then assigned later. Unlike string/boolean/number, the Function type name is capitalized.
let greet: Function;
// Error: Type 'string' is not assignable to type 'Function'
// greet = 'hello';
greet = () => {
console.log("hello, again");
};

typed parameters
Parameter types are annotated with a colon after each parameter name. Arguments passed at the call site must match, or compilation fails.
const add = (a: number, b: number) => {
console.log(a + b);
};
add(5, 10); // logs 15
add(5, "10"); // Error: Argument of type 'string' is not assignable to parameter of type 'number'
Omitting a required argument is also an error — every required parameter must be supplied.
optional parameters (?) and union types
Appending ? to a parameter makes it optional. A union type (e.g. number | string) widens what the parameter accepts. An omitted optional parameter is undefined at runtime.
const add = (a: number, b: number, c?: number | string) => {
console.log(a + b);
console.log(c);
};
add(5, 10); // logs 15, then undefined
default parameters
A default value makes a parameter effectively optional without needing ? — do not use both together. When the caller omits the argument, the default applies; when the caller supplies one, it overrides the default.
const add = (a: number, b: number, c: number | string = 10) => {
console.log(a + b);
console.log(c);
};
add(5, 10); // logs 15, then 10 (default)
add(5, 10, 20); // logs 15, then 20 (override)
add(5, 10, "20"); // logs 15, then '20' — allowed by the union type

(On screen the default literal reads 18 and the final call reads add(5, 10, '20');; the spoken walkthrough uses 10. Either literal demonstrates the same mechanism.)
Rule of thumb: required parameters first, optional/defaulted parameters last, or positional arguments get mixed up.
inferred return types
When a function returns a value, TypeScript infers the return type, and any variable initialized from the call inherits that type.
const minus = (a: number, b: number) => {
return a + b;
};
let result = minus(10, 7); // result: number
// Error: Type 'string' is not assignable to type 'number'
result = "hello";
explicit return-type annotation
The return type can be declared explicitly after the parameter list with a colon. It is redundant when inference already covers it, but useful as self-documentation on larger functions so readers see the contract at a glance.
const add = (a: number, b: number, c: number | string = 10): number => {
console.log(a + b);
console.log(c);
return a + b;
};
void vs undefined
A function that logs but returns nothing still has a return type: void — a complete absence of any return value (visible in the editor hover tooltip as => void). Do not confuse it with undefined:
undefined= a real value, e.g. what an omitted optional parameter holds.void= no value at all. When compiled to JavaScript it surfaces asundefinedat runtime, but in TypeScript the two are distinct types.
full evolved example (end of lesson)
let greet: Function;
// greet = 'hello'; // Error
greet = () => {
console.log("hello, again");
};
const add = (a: number, b: number, c: number | string = 10) => {
console.log(a + b);
console.log(c);
};
add(5, 10, "20");
Next video teaser: pinning down exactly which functions a variable may hold — 010 — Function Signatures.
Prev: 007 — Project Structure with tsconfig · Next: 009 — Type Aliases
Module 04 covered: inferred function type, explicit Function type, typed parameters with arity enforcement, optional (?) and default parameters with required-first ordering, inferred versus explicit return types, void versus undefined; signatures and generics come later. Transcript notes: booleans, Function capitalized versus lowercase primitives, greet, TypeScript, const minus/let result; frames 1-5 and 7-9 are talking-head shots, code in frames 6 and 10.