Quick guide to Function Overloading in TypeScript

We use functions all the time in our apps, generally speaking most of the JS code are functions. TypeScript gives us many ways to describe them.
For a basic function, this is fairly easy to do, but what if the function takes a variety of argument count…


This content originally appeared on DEV Community and was authored by Makar Murashov

We use functions all the time in our apps, generally speaking most of the JS code are functions. TypeScript gives us many ways to describe them.
For a basic function, this is fairly easy to do, but what if the function takes a variety of argument counts and types, or even returns a different type depending on how it's called?
For such cases, TypeScript has the handy function overloading feature. Let's see how to use it and how it can help you improve your code.

Function typing

I feel hungry now, so let's create a function that will cook a dish:

function cookDish(ingredient: string): string {
  return `${ingredient}🍴 is ready, bon appétit!`;
}

We passed a single string argument as an ingredient and it returns a string dish after invocation:

cookDish('🥚'); // '🍳🍴 is ready, bon appétit!'

But wait, this is not enough, I definitely need a sandwich here!
To cook it, we need to modify our function, so that it could accept multiple ingredients:

function cookDish(ingredient: string | string[]): string {
  const tableSet = '🍴 is ready, bon appétit!';
  if (typeof ingredient === 'string') {
    return `${ingredient}${tableSet}`;
  } else if (Array.isArray(ingredient)) {
    return `${ingredient.join('')}${tableSet}`
  }
  throw new Error('Nothing to cook 😭');
}

We used Union type to describe our function argument, that can be either one string or multiple string[] of them:

cookDish('🌽'); // '🍿🍴 is ready, bon appétit!';
cookDish(['🍞', '🍅', '🥓']); // '🥪🍴 is ready, bon appétit!';

Adding types to support various arguments is a common and good approach in most cases, but sometimes you need to explicitly define all the ways to call a function. This is where function overloading comes into play.

Function overloading

In the case of a rather complex function, to improve usability and readability, it is always better to use the function overloading feature to improve usability and readability. This approach is considered the most flexible and transparent.

To use this, we need to write some function signatures:

  1. Overload signature - defines different ways to call a function: arguments and return types, and doesn't have a body. There can be multiple overload signatures (usually two or more).
  2. Implementation signature - provides an implementation for a function: function body. There can be only one implementation signature and it must be compatible to overload signatures.

Let's rewrite our cookDish using function overloading:

// Overload signature
function cookDish(ingredient: string): string
function cookDish(ingredients: string[]): string

// Implementation signature
function cookDish(ingredient: any): string {
  const tableSet = '🍴 is ready, bon appétit!';
  if (typeof ingredient === 'string') {
    return `${ingredient}${tableSet}`;
  } else if (Array.isArray(ingredient)) {
    return `${ingredient.join('')}${tableSet}`
  }
  throw new Error('Nothing to cook 😭');
}

Two overload signatures describe two different ways the function can be called: with string or string[] argument. In both ways we will get a cooked string dish as a result.
An implementation signature defines the behavior of a function within a function body.
Our function invocation doesn't change though, we can cook as before:

cookDish('🍚'); // '🍙🍴 is ready, bon appétit!';
cookDish(['🫓', '🍅', '🥑']); // '🥙🍴 is ready, bon appétit!';

const money: any = 100;
cookDish(money);
/**
⛔ No overload matches this call.
Overload 1 of 2, '(ingredient: string): string', gave the following error.
  Argument of type 'any' is not assignable to parameter of type 'string'.
Overload 2 of 2, '(ingredients: string[]): string', gave the following error.
  Argument of type 'any' is not assignable to parameter of type 'string[]'.
*/

Note at the last example above: money can't cook you a dish although an implementation signature is the one that implements our function, it cannot be called directly, even though it accepts any as an argument function cookDish(ingredient: any). You can call only overload signatures.

It's dinner time! let's look at a slightly more complex example:

function cookDinner(dish: string): string
function cookDinner(money: number): string // Wrong argument type
/**
⛔ This overload signature is not compatible with its implementation signature.
*/
function cookDinner(dish: string, drink: string, dessert: string): string
function cookDinner(dish: string, drink?: string, dessert?: string): string {
  let dinner = `${dish}🍴`
  if (drink && dessert) {
    dinner += ` ${drink}🧊${dessert}🥄`
  }
  return `${dinner} is ready, bon appétit!`
}

cookDinner('🍝'); // '🍝🍴 is ready, bon appétit!';
cookDinner('🍔', '🥤', '🍰'); // '🍔🍴🥤🧊🍰🥄 is ready, bon appétit!';

cookDinner('🍺', '🍸') // 🤒 Invalid number of arguments
/**
⛔ No overload expects 2 arguments, but overloads do exist that expect either 1 or 3 arguments.
*/

Need to remember that implementation signature must be compatible to overloads and can't be called directly.

Conclusion

Function overloading is a powerful TypeScript feature that allows you to type your functions more elegantly.

More read:

Hope you enjoyed this guide, stay tuned for more.


This content originally appeared on DEV Community and was authored by Makar Murashov


Print Share Comment Cite Upload Translate Updates
APA

Makar Murashov | Sciencx (2022-06-16T13:45:57+00:00) Quick guide to Function Overloading in TypeScript. Retrieved from https://www.scien.cx/2022/06/16/quick-guide-to-function-overloading-in-typescript/

MLA
" » Quick guide to Function Overloading in TypeScript." Makar Murashov | Sciencx - Thursday June 16, 2022, https://www.scien.cx/2022/06/16/quick-guide-to-function-overloading-in-typescript/
HARVARD
Makar Murashov | Sciencx Thursday June 16, 2022 » Quick guide to Function Overloading in TypeScript., viewed ,<https://www.scien.cx/2022/06/16/quick-guide-to-function-overloading-in-typescript/>
VANCOUVER
Makar Murashov | Sciencx - » Quick guide to Function Overloading in TypeScript. [Internet]. [Accessed ]. Available from: https://www.scien.cx/2022/06/16/quick-guide-to-function-overloading-in-typescript/
CHICAGO
" » Quick guide to Function Overloading in TypeScript." Makar Murashov | Sciencx - Accessed . https://www.scien.cx/2022/06/16/quick-guide-to-function-overloading-in-typescript/
IEEE
" » Quick guide to Function Overloading in TypeScript." Makar Murashov | Sciencx [Online]. Available: https://www.scien.cx/2022/06/16/quick-guide-to-function-overloading-in-typescript/. [Accessed: ]
rf:citation
» Quick guide to Function Overloading in TypeScript | Makar Murashov | Sciencx | https://www.scien.cx/2022/06/16/quick-guide-to-function-overloading-in-typescript/ |

Please log in to upload a file.




There are no updates yet.
Click the Upload button above to add an update.

You must be logged in to translate posts. Please log in or register.