每当从数组添加或删除元素时获取事件

时间:2015-09-03 06:05:45

标签: ios arrays swift nsmutablearray

我有一个包含自定义对象的数组。现在我需要做的是什么时候添加或删除一个元素我需要一个方法来调用totalCost。有可能??

class Company {
    var name: String?
    ....
    ....
    var employees[Employee] = []
    var totalCost: Float = 0
}

class Employee {
    var name: String?
    .....
    .....
    var salary: Float = 0
}

我可以选择覆盖totalCost的getter方法,我需要遍历所有员工对象来计算totalCost。但是我不想这样做,因为我可能拥有大量的员工,而且每次调用这次迭代都是一项昂贵的操作。

任何建议都会令人感激。

3 个答案:

答案 0 :(得分:3)

您可以创建一个只读的计算属性,如下所示:

class Employee {
    var name: String?
    var salary: Float = 0
    init(name: String, salary:Float) {
        self.name = name
        self.salary = salary
    }
}



class Company {
    var name: String?
    var employees:[Employee] = []
    var totalCost: Float  {
        return employees.map{$0.salary}.reduce(0){$0+$1}
    }
}


let employee1 = Employee(name: "Steve", salary: 5000)
let employee2 = Employee(name: "Chris", salary: 7000)
let employee3 = Employee(name: "John", salary: 3000)

let company = Company()
company.name = "ACME"
company.employees = [employee1,employee2,employee3]
company.totalCost   // 15000

答案 1 :(得分:0)

您可以对Array类进行扩展,您可以在其中覆盖append,insert,remove(atIndex),...并添加总计算方法。

请确保覆盖用于添加/删除的所有方法(例如,如果您使用它,请不要忘记+ =!

还要考虑到,如果更改Employee的工资,还必须计算totalCost(此处不涉及任何数组操作,因此不会触发这些方法)。

您可以通过不反复计算所有员工来提高效率:例如追加方法:添加新员工的总数,删除方法:在您的覆盖方法中首先在删除前减去,工资的setter方法:减去从总计老,添加到总... 再小心,因为如果你忘记了什么,你可能会出错!

答案 2 :(得分:0)

你可以按照这种方法制作一个观察者和通知:

数组类中的

执行此操作:

let arrayChangedNotification = "myArrayDidChange"

class Company {
var name: String?
....
....
var employees: [Employee] = []{
didSet{
alertMe()
}
}
var totalCost: Float = 0

func alertMe() {
    let center = NSNotificationCenter.defaultCenter()
    center.postNotificationName(arrayChangedNotification, object: self)
}
}

并在你的viewController中添加:

func arrayDidChange(notification: NSNotification) {
 // whatever gonna happen in array change!
}

并在viewDidLoad()方法中将观察者添加到通知:

let center = NSNotificationCenter.defaultCenter()
    center.addObserver( self,
        selector: "arrayDidChange:",name: arrayChangedNotification,object: nil)