Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

error: extraneous argument label 'no1:' in call [duplicate]

Tags:

swift

Consider the code given below

class division {
    var count: Int = 0
    func incrementBy(no1: Int, no2: Int) {
        count = no1 / no2
        println(count)
    }
}

let counter = division()
counter.incrementBy(no1:1800, no2: 3)

It gives following error :

error: extraneous argument label 'no1:' in call
counter.incrementBy(no1:1800, no2: 3)
                   ^~~~~

When I remove the label no1, compiler doesn't complain for the label no2.

When I remove both levels no1 and no2, it gives following error :

error: missing argument label 'no2:' in call
counter.incrementBy(1800,  3)
                   ^
                           no2: 

Can anyone please explain this behaviour. Thanks in advance.

like image 382
Jayram Kumar Avatar asked Dec 18 '22 18:12

Jayram Kumar


1 Answers

Swift 3

The contents of this answer (written for Swift 2.2 bbelow) is all mostly still applicable, but with the difference that the following default behavior now holds in Swift 3:

  • All the function parameters have the same external parameter name as the internal one, unless otherwise specified.

I.e., the first function parameter no longer has an empty (omitted, _) external parameter name, per default, as was the case in Swift 2.2.

For additional details, see the following accepted and implemented Swift Evolution proposal:

  • SE-0046: Establish consistent label behavior across all parameters including first labels

Swift 2

Functions: external and internal parameter names

For any function in Swift, the function parameters has internal as well as external parameter names. By default, the following default behaviour holds:

  • The first function parameter has an empty (omitted, _) external parameter name.
  • All the following parameters have the same external parameter name as the internal one, unless otherwise specified.

Hence, following function

func foo(first: Int, second: Int) {}

is called as

foo(1, second: 2)
//  |     \
//  |   by default, same external as internal parameter name
//   \
//    by default, no external parameter name  

Now, you can naturally specify whether also the first function parameter should have an external name (which then needs to be specified when calling the function):

func foo(firstExternal first: Int, second: Int) {}

// called as
foo(firstExternal: 1, second: 2)

Likewise, you may specify that you want the second parameter to have no external name (omitted) by specifying the external name as an underscore _.

func foo(first: Int, _ second: Int) {}

// called as
foo(1, 2)

If we return to the first example above (default behaviour), we realize that if we specify no external names, e.g.

func foo(first: Int, second: Int) {}

we get a "default" function signature (w.r.t. external parameter names) that is the equivalence of the following explicitly stated external names:

func foo(_ first: Int, second second: Int) {}
//       |               \
//       |       same external as internal parameter name
//        \
//    no (omitted) external parameter name

For additional details, see

  • The Language Guide - Functions

Your specific example

Using the knowledge from above, we can apply it to your specific example, looking only at the signature of your function incrementBy:

func incrementBy(no1: Int, no2: Int) { ... }
//               |          \
//               |    no explicitly stated external names: hence, since
//               |    this is not the first parameter, the external name
//               |    is set to the same as the internal name (no2), by default
//                \
//       no explicitly stated external names: hence, since this is the
//       first parameter, the external name is omitted, by default  

Hence, we call your function incrementBy as

incrementBy(1, no2: 2)

With this, we also realize why your two own attempts---included in your question---yields errors:

Error #1

error: extraneous argument label 'no1:' in call
counter.incrementBy(no1:1800, no2: 3)

As explained by this error message, you have an extraneous argument label for the first function argument: as covered above, the first function parameter has an omitted external parameter name by default (which is in effect in your example), and hence, when calling it, we should include no argument label for the first parameter.

Error #2

error: missing argument label 'no2:' in call
counter.incrementBy(1800,  3)

This attempted call, on the other hand, correctly omits external parameter name label for the first argument, but does so also for the second argument. The second function parameter of incrementBy, however, has the same external parameter name as its internal one, and hence, the external parameter name label no2: must be included in the call to the function.

like image 73
dfrib Avatar answered Jan 28 '23 00:01

dfrib