快速添加或更新基于唯一属性ID的项目数组

时间:2018-10-16 07:42:06

标签: ios arrays swift

我正在寻找可以将对象数组(对象是类而不是结构)添加到现有数组中的有效算法。要求是如果现有数组包含具有相同id的对象,则函数将更新该对象(根据更新的对象更改现有对象的属性)。如果object.id未包含在现有数组中,该函数将简单地将该对象添加到现有数组中。返回数组由新对象和更新对象组成。

基本上仅在object.id是新对象时添加对象。如果已经包含object.id,它将更新对象的属性

我可以在下面尝试

func addPhotoArray(_ photos: [Photo], addedPhoto: [Photo]) -> [Photo]{
        var resultArray = photos
        let originalIds = photos.map{$0.id}

        for photo in addedPhoto {
            if !originalIds.contains(photo.id) {
                resultArray.append(photo)
            }
        }
        return resultArray
    }

但是我缺少更新要求。我该如何解决这个问题?

更新

用索引替换项目是一个选项。但是,如果仅更改1个或2个属性或什么都没有更改,则不确定是否有效。我也在考虑使用Set。如何遵循哈希函数,我们可以如下使用联合函数

extension Photo {
    static func union (left: [Photo],right: [Photo] ) -> [Photo]{
        return Array(Set(left).union(Set(right)))
    }

    static func ==(lhs: Photo, rhs: Photo) -> Bool {
        return lhs.id == rhs.id
    }
}

3 个答案:

答案 0 :(得分:2)

我选择不使用ID的数组,而是使用firstIndex查找重复的照片(我假设原始数组中的所有照片都是唯一的),如果找到了照片,则将其替换为新版本。

func addPhotoArray(_ photos: [Photo], addedPhoto: [Photo]) -> [Photo]{
    var resultArray = photos

    for photo in addedPhoto {
        if let photoIndex = resultArray.firstIndex(where: { $0.id == photo.id}) {
            resultArray[photoIndex] = photo
        } else {
            resultArray.append(photo)
        }
    }
    return resultArray
}

答案 1 :(得分:1)

类型为[YourIdType: YourObjectType]的词典是您的解决方案。插入和检索成本为O(1)。在您的情况下,最糟糕的情况是O(n),其中n = addedArray.count

有关Dictionary

的更多信息

答案 2 :(得分:1)

您可以尝试以下方法:

func addPhotoArray(_ photos: [Photo], addedPhoto: [Photo]) -> [Photo]{
    var resultArray = photos
    for photo in addedPhoto {
        // Search for the object is it already exists
        if let existingPhotoIndex = photos.firstIndex(where: { (tempPhoto) -> Bool in
                return photo.id == tempPhoto.id
            }) {
             resultArray[existingPhotoIndex] = photo // Replace the object 
        }
        else {
            resultArray.append(photo) // Insert new Object
        }
    }
    return resultArray
}

如果需要,您可以进一步改进。