Swift Function Overloading

In this article, you will learn about function overloading, when do we need function overloading and how to overload with examples.

Two or more functions having same name but different argument(s) are known as overloaded functions.

Why do we need function overloading?

Imagine you are developing a shooter game where the player can attack its enemies using a knife, a blade and a gun. Your solution for the attack functionality might be defining the actions into functions as:

func attack() {
    //..
    print("Attacking with Knife")
}

func attack() {
    //..
    print("Attacking with Blade")
}

func attack() {
    //..
    print("Attacking with Gun")
}

But when you try to run the above program, you will get a compile time error in Swift as 'attack()' previously declared here. However, another solution might be defining different function names for the particular functionality as:

struct Knife {
}
struct Gun {
}
struct Blade {
}

func attackUsingKnife(weapon:Knife) {
    //..
    print("Attacking with Knife")
}

func attackUsingBlade(weapon:Blade) {
    //..
    print("Attacking with Blade")
}

func attackUsingGun(weapon:Gun) {
    //..
    print("Attacking with Gun")
}

Don’t worry if you don't know what struct is. For now just think of it as something that creates a physical object in programming, so you’re creating a knife, gun and blade. If you want to know more, see Swift Struct. If not, we'll come back to it in the later chapters.

The only problem with this solution is you need to remember the function names to call that particular attack action. Also as the level rises, the player may have additional features for attack using bomb, grenade, shotgun, etc.

Creating function with different names is time consuming and increases overhead of remembering the function name to call it. All in all, it's not intuitive.

It would be much better if you could create different functions with the same name but different implementation for each weapon. In this way, remembering one function name is enough and you wouldn't have to worry about the function names for other weapons.


What is function overloading?

The process we just described is known as function overloading. By definition, the process of creating two or more than two functions with the same name but having different number or types of parameters passed is known as function overloading.

Let's see this in below example:

Example 1: Function Overloading

struct Knife {
}
struct Gun {
}
struct Blade {
}

func attack(with weapon:Knife) {
    print("Attacking with Knife")
}

func attack(with weapon:Gun) {
    print("Attacking with Gun")
}

func attack(with weapon:Blade) {
    print("Attacking with Blade")
}

attack(with: Gun())
attack(with: Blade())
attack(with: Knife())

When you run the above program, the output will be:

Attacking with Gun
Attacking with Blade
Attacking with Knife

In the above program, we have created three different functions with the same name attack. However, it accepts different parameter types. This way remembering attack name to call the function is enough.

  • The call attack(with: Gun()) triggers the statement inside the function func attack(with weapon:Gun).
  • The call attack(with: Blade()) triggers the statement inside the function func attack(with weapon:Blade).
  • The call attack(with: Knife()) statement inside the function func attack(with weapon:Knife).

Example 2: Function Overloading based on different parameter types

func output(x:Int) {
    print("The int value is \(x)")
}

func output(x:String) {
    print("The string value is \(x)")
}

output(x: 2)
output(x: "Swift")

When you run the above program, the output will be:

The int value is 2
The string value is Swift

In the above program, we’ve two functions with the same name output() and same number of parameters. However, the first output() function takes an integer as a parameter, and the second output() function takes String as a parameter.

Similar to the Example 1,

  • the call to output(x: 2) triggers the statement inside the function func output(x:Int) and
  • the call to output(x: "Swift") triggers the statement inside the function func output(x:String).

Example 3: Function Overloading based on different number of parameters

func output() {
    print("Good Morning!")
}

func output(text:String) {
    print(text)
}

func output(text:String, num:Int) {
    print("\(text)\(num)!")
}

output()
output(text: "Good Evening!")
output(text1: "Good N", num: 8)

When you run the above program, the output will be:

Good Morning!
Good Evening!
Good Night!

In the above program, the function output() has been overloaded based on the number of arguments.

The first output() takes no parameters, the second output() takes a single parameter: String, and the third output() takes two parameters: String and Int.

Lets try to overload by changing the parameter name but keeping the argument label same as:


Example 4: Function overloading with same argument label

func output(value text:String) {
    print(text)
}

func output(value num:Int) {
    print(num)
}

output(value: 2)
output(value: "Hello")

When you run the above program, the output will be:

2
Hello

As you can see, in the above program, you can use the same argument label for the overloaded functions. However, as overloading requires, you must have either different number of parameters or different types of parameters.