使用它的通用 ObjectType 的 PHFetchResult 扩展?

PHFetchResult extension that uses it's Generic ObjectType?

我正在尝试向 PHFetchResult 添加扩展以将结果对象作为正确类型的数组拉出 - 到目前为止,我无法弄清楚如何避免下面看到的复制。除了类型约束之外,以下扩展是相同的。如果我使用 PHObject 作为约束,它会起作用,但结果需要转换为更具体的类型...

extension PHFetchResult where ObjectType == PHAsset {
    var objects: [ObjectType] {
        var _objects: [ObjectType] = []
        enumerateObjects { (object, _, _) in
            _objects.append(object)
        }
        return _objects
    }
}    
extension PHFetchResult where ObjectType == PHCollection {
    var objects: [ObjectType] {
        var _objects: [ObjectType] = []
        enumerateObjects { (object, _, _) in
            _objects.append(object)
        }
        return _objects
    }
}    
extension PHFetchResult where ObjectType == PHAssetCollection {
    var objects: [ObjectType] {
        var _objects: [ObjectType] = []
        enumerateObjects { (object, _, _) in
            _objects.append(object)
        }
        return _objects
    }
}

这是在 ObjC 中定义并导入到 Swift 的泛型类型的普遍问题。一些相关的编译器错误:

简而言之:ObjC 泛型是 type-erasing,Swift 泛型是 type-preserving。您需要后者来完成定义 type-constrained 扩展等任务,但您不能这样做,因为 Swift 对任何特定 PHFetchResult 实例的对象类型一无所知。

将广泛的 ObjC 泛型导入到 Swift 3 的 swift-evolution 提案包括让 ObjC classes 在运行时提供有关其泛型类型参数的信息的规定...但是截至今天,该规定从未得到执行。

AFIAK,这个问题并没有真正的解决方案(除了致力于 Swift 编译器项目以改进 ObjC 泛型支持),也没有类似的问题,例如使 PHFetchResult 符合 [=12] =] 或 Collection

(我已经尝试了几个角度来扩展 PhotoKit classes 以使其更 Swifty 我自己,但没有太大成功。关于我唯一没有尝试过的事情 - 主要是因为它是如此严厉的措施 — 是 wrapping/replacing 大块的 API。不过理论上,您可以将 PHFetchResult 包装在 non-generic ObjC class 中,然后包装在通用 Swift 类型中,并将所有 PhotoKit 获取方法替换为提供包装器类型的适当专用版本的方法。)