核心数据按距当前用户位置的距离进行过滤

时间:2020-04-29 19:25:29

标签: database core-data realm nsfetchedresultscontroller yapdatabase

我有一个NSManagedObject类,该类保留在Core Data的SQLite数据库中。该对象具有持久的纬度和经度属性。我正在尝试创建一个NSFetchedRequestController,以获取该类的所有实例,这些实例都在距用户一定距离内。做过一些研究之后,使用Core Data似乎无法做到这一点,因为Core Data仅支持边界框样式查询,而不支持带有块的谓词。

例如,我有一类具有纬度和经度属性的网上论坛。给定纬度和经度(例如,用户的纬度和经度),请提取位于给定纬度和经度6英里半径内的所有组。

class Group{
     var latitude: Float
     var longitude: Float
}

我想利用Core Data的R-Tree索引功能对用户附近我的类的实例的经度和纬度进行快速边界框查询。然后,我想使用更精确的谓词过滤结果,使用自己的代码块查看哪些实例在用户当前位置内。这是“边界框”查询。

let request: NSFetchRequest<Group> = Group.fetchRequest()
let (topLeft,bottomRight) = boundingBox(center: center, radius: searchRadius)
let maxLat = topLeft.latitude
let minLon = topLeft.longitude
let minLat = bottomRight.latitude
let maxLon = bottomRight.longitude
let predicate = NSPredicate(format: "(%f < longitude AND longitude < %f) AND (%f < latitude AND latitude < %f)", minLon, maxLon, minLat, maxLat)
request.predicate = predicate

问题是我想要一个看起来像这样的提取:

let location: CLLocation = /* Initialize a CLLocation */

let predicate = NSPredicate { (obj, _) -> Bool in
     let object = obj as! Group
     let objLocation = CLLocation(latitude: Double(object.latitude), longitude: Double(object.longitude))
     return location.distance(from: objLocation) < 9656 //6 miles in meters
}

NSFetched结果控制器不允许带块谓词。这两个访存之间存在显着差异。前者将所有组都放在边界框内(minLat,minLon,maxLat和maxLat),后者则将所有组都添加到给定半径的圆中。

然后我想使用NSFetchedRequestController在表中显示结果,并利用不错的自动更新功能。但是,当然,Core Data仅支持边界框样式查询,而不支持我需要的两步过滤方法。有适当的解决方案吗?

如果Core Data根本无法使用这种类型的数据库,我愿意使用其他数据库。我看了看YapDatabase,它看起来更灵活,并且包含R-Tree索引,但是我担心它没有得到很好的支持。 Realm不支持R-Tree索引。

0 个答案:

没有答案
相关问题