2016-11-17 149 views
2

在Xcode中操场关闭的阵列做实验,我收到此错误:斯威夫特:暧昧使用运营商的“*”

Playground execution failed: error: closures.playground:11:25: error: ambiguous use of operator '*' 
      {x in x * x}, 

我不明白了一个道理语法为什么这是不工作的,但它应该是

我的初始闭合是:

let f = {(x: Int) -> Int 
    in 
    return x + 42} 

我然后将如此限定的数组:

let closures = [f, 
      {(x:Int) -> Int in return x * 2}, 
      {x in return x - 8}, 
      {x in x * x}, //This line causes the error. 
      {$0 * 42}] 

每个封闭件的符合f的签名,所以这是在Xcode错误?如果不是,发生了什么?

要燕尾上,不应类型在一种情况下可以推断,就像它是在所有其他情况下明确推断?

编辑:雨燕2.2,这似乎很好地工作,但我使用Swift3。

+0

这似乎很好地工作,如果我们替换'X * x'与让说,'X * 8'。或者与一些常数相乘。 –

+0

@RajanMaheshwari这是真的,但'x * x'遵循Swift语法规则,并且不起作用,这对我来说似乎有点儿麻烦。 – NonCreature0714

+0

我猜它是因为编译器无法找到x变量与自身相乘的类型,因为它给出的数据类型为。然而,乘以一些int常量使其成为编译器 –

回答

1

我有一个理论,如果你愿意沿着这里遵循:

使用您的f定义,下面一行导致不同的错误在雨燕2.2和雨燕3.0:

let closures = [f, { $0 * 4.5 },{$0 * 42}] 

注意的第二个元素是由双相乘,使X的推断类型为Double一样,所以关闭签名不匹配。

在夫特2.2:“表达的类型是没有更多的上下文模糊”

在夫特3.0:“异源收集字面只能被推断为‘[任何]’;添加显式类型注释如果这是故意的”

这似乎表明Swift 3.0编译器可以识别不同封闭签名的可能性,可能会将其作为同质元素类型降级到Any

在您的例子:

let closures = [f, 
     {(x:Int) -> Int in return x * 2}, 
     {x in return x - 8}, 
     {x in x * x}, //This line causes the error. 
     {$0 * 42}] 

导致错误有x没有明确的类型的线。 Swift 3.0允许x可能是某种其他类型的可能性,例如, Double,Float等,并且整个阵列可以被设计为具有类型[Any]而不是[(Int)->Int]。因此,通过不声明在此位置x任何明确的类型,或者closures作为一个整体,它并不清楚该*功能的版本应该是选择的编译器。也许这些x都是双打?花车?由于closures数组的类型不明确,并且x的类型不明确,因此编译器无法确定应使用哪个版本的*以及操作数类型是什么。

因此,您可以通过修复该错误使得阵列的类型明确,即:

let closures:[(Int)->Int] = [f, 
     {(x:Int) -> Int in return x * 2}, 
     {x in return x - 8}, 
     {x in x * x}, //No more error. 
     {$0 * 42}] 

或者,通过使x类型封明确的,即内:

let closures = [f, 
     {(x:Int) -> Int in return x * 2}, 
     {x in return x - 8}, 
     {(x:Int) in x * x}, //No more error. 
     {$0 * 42}] 

在其它封闭件,其它操作数的x相反足以用于编译器推断x类型,但在生成错误封闭,没有什么会决定性明确的类型。

此外,它似乎在Swift 2.2中起作用,因为Swift 2.2不会将异构数组推断为[Any]类型,因此假定所有闭包都必须具有相同的类型。在Swift 3中,似乎允许一些模糊的可能性,这使得编译器不太确定你的意图。

至少这是我的理论:)

+0

这是一个很好的观察,尽管在Swift2.2中,这些封闭按原样工作。所以这就是我困惑的原因。 – NonCreature0714

+0

@ NonCreature0714我挖的更深一点,改变了我的答案,以反映_theory_,为什么它工作在斯威夫特2.2而不是3.0斯威夫特我 –

+0

会在明天早晨,当我在我的笔记本电脑好好看看! – NonCreature0714

0

我不知道它听起来是否正确,但x变量没有类型。它不是通过操作推断出任何其他常数的类型。

它是< <错误类型>>。所以编译器发现是ambiguos

enter image description here