view raw
John Scalo John Scalo - 11 months ago 60
Swift Question

Accessing only a subset of anonymous closure arguments

I'm having some trouble understanding the usage of anonymous closure arguments. To illustrate I whipped this contrived example up in a playground:

typealias SomeClosureType = (
thing0: Float,
thing1: Float,
thing2: Float,
thing3: Float,
thing4: Float,
thing5: Float
) -> Void

class MyClass {

var someClosure: SomeClosureType!

init() {
// This is OK but long
self.someClosure = { (thing0: Float, thing1: Float, thing2: Float, thing3: Float, thing4: Float, thing5: Float) in self.handleThing0(thing0) }

// Compiler error: "cannot assign value of type '(Float) -> ()' to type 'SomeClosureType!'"
self.someClosure = { self.handleThing0($0) }

func handleThing0(thing0: Float) {

let myInstance = MyClass()
myInstance.someClosure(thing0: 0, thing1: 1, thing2: 2, thing3: 3, thing4: 4, thing5: 5)

So basically when I try to access anonymous closure arguments from within the closure, I get this error. What am I missing?


To the compiler, it looks like your closure is only handling a single float parameter, because your closure never references the other 5 "things" in any way. So there is an apparent mismatch and the compiler flags it as an error.

If you reference all 6 input parameters in any valid way, the error will disappear. For example, although this is not something you should ever write, merely referencing the additional parameters like this will be valid:

self.someClosure = { self.handleThing0($0); _ = [$1,$2,$3,$4,$5] }

The shortest / best possible way to express what you are going for is:

self.someClosure = { thing0, _, _, _, _, _ in self.handleThing0(thing0) }

where each _ represents a value you are ignoring, but the compiler can infer that they would be Float values.