Swift can't infer type of expression with multiple overloads and multiple return branches

Originator:hello
Number:rdar://23385956 Date Originated:11/3/2015
Status:Open Resolved:No
Product:Developer Tools Product Version:Swift 2.1
Classification: Reproducible:Always
 
Summary:
The compiler is not yet capable of inferring the type of an expression when multiple overloads are involved.

Steps to Reproduce:
Compile the following code:

enum A {
	case A1
	case A2
}
enum B {
	case B1
}
enum C {
	case C1
}

struct S {
	func f(a: A, f: A -> B) -> B {
		return f(a)
	}

	func f(a: A, f: A -> C) -> C {
		return f(a)
	}
}

let s = S()

// This compiles because there’s only one branch.
let _ = s.f(.A1) { _ in
	return .B1
}

// This is ambiguous: it requires either an explicit type on the return value, or in the closure
let _ = s.f(.A1) { a in
	switch a {
	case .A1: return .B1
	case .A2: return .B1
	}
}

Expected Results:
Code compiles, and the second expression evaluates to type `B`.

Actual Results:
Error: ambiguous use of 'f(_:f:)'
let _ = s.f(.A1) { a in
        ^
/var/folders/yt/njd3fm3x4jd54hgtnck226l00000gn/T/./lldb/83520/playground61.swift:13:7: note: found this candidate
        func f(a: A, f: A -> B) -> B {
             ^
/var/folders/yt/njd3fm3x4jd54hgtnck226l00000gn/T/./lldb/83520/playground61.swift:17:7: note: found this candidate
        func f(a: A, f: A -> C) -> C {

Notes:
A workaround is to explicitly specify the types:

// This compiles thanks to the explicit type in the return value.
let _: B = s.f(.A1) { a in
	switch a {
	case .A1: return .B1
	case .A2: return .B1
	}
}

// This compiles thanks to the explicit type in the closure.
let _ = s.f(.A1) { a -> B in
	switch a {
	case .A1: return .B1
	case .A2: return .B1
	}
}

However, with more complex scenarios this becomes harder to manage, as well as harder to decipher why the compiler can’t infer the type.

Comments


Please note: Reports posted here will not necessarily be seen by Apple. All problems should be submitted at bugreport.apple.com before they are posted here. Please only post information for Radars that you have filed yourself, and please do not include Apple confidential information in your posts. Thank you!