0

看来我遇到了与 SwiftindexOf功能不一致的行为。

indexOfSwift中有两个函数:
1. 第一个Equatable作为参数:array.indexOf(obj)
2. 第二个将匹配的闭包作为参数:array.indexOf{$0 == obj}

我有一个定义了运算符的NSObject子类==,即它符合Equatable,因此,我假设两个函数的工作方式完全相同(在示例中使用闭包)。

但是,该1st方法的行为不一致,特别是nil在使用对象调用时返回,该对象的实例不存在于数组中。

为了说明问题,我提供了带有注释的示例代码:

class EqObj: NSObject {
  let value: Int
  init(value: Int) {
    self.value = value
  }
}

func ==(lhs: EqObj, rhs: EqObj) -> Bool{
  return lhs.value == rhs.value
}

var array = [Obj(value: 1), Obj(value: 3), Obj(value: 5)]
var object = Obj(value: 5)

// returns nil, should return 2 - incorrect
array.indexOf(object) // Instance is not present
// returns 2, correct
array.indexOf(array.last!) // Instance is present
// returns 2, correct
array.indexOf{$0 == object} // Instance is not present, predicate
// returns non-empty array, correct
array.filter{$0 == object} // Instance is not present, predicate

这个问题只能用NSObject子类重现。当我更改Obj: NSObjectObj: Equatable方法indexOf()完全按预期工作时,即返回2.

问题是这是否可以被认为是一个错误?

我的假设是array.indexOf(object)调用isEqual方法NSObject而不是我的重载==运算符。

我的解决方案: 我使用array.indexOf{$0 == object}

4

1 回答 1

0

首先,有了这个定义,我得到了不同的结果

class Obj: NSObject {
    let value: Int

    init(value:Int) {
        self.value = value
    }
}

func ==(lhs: Obj, rhs: Obj) -> Bool{
    return lhs.value == rhs.value
}

var array = [Obj(value: 1), Obj(value: 3), Obj(value: 5)]
var object = Obj(value: 5)

他们来了

在此处输入图像描述

您可以阅读以下每个结果后的原因

结果#1

array.indexOf(object) // nil

在这种情况下,使用 isEqual 方法,因此您只是在比较内存地址。并且由于objectvar 引用了不在数组内的对象,因此您得到nil了结果

结果#2

array.indexOf(array.last!) // 2

再次isEqual被使用。但是,在这里您将传递给indexOf数组中最后一个对象的引用,因此它可以工作。

结果#3

array.indexOf { $0 == object } // 2

在这里,您显式使用了==您定义的运算符,因此使用了该value属性。

结果#4

array.filter { $0 == object } // [{NSObject, value 5}]

再次使用==运算符,然后使用value属性检查是否相等。

于 2016-08-03T11:03:56.200 回答