Database 按与当前用户位置的距离筛选核心数据

Database 按与当前用户位置的距离筛选核心数据,database,core-data,realm,nsfetchedresultscontroller,yapdatabase,Database,Core Data,Realm,Nsfetchedresultscontroller,Yapdatabase,我有一个NSManagedObject类,它保存在核心数据中的SQLite数据库中。此对象具有持久的纬度和经度属性。我正在尝试创建一个NSFetchedRequestController,用于获取该类与用户之间一定距离内的所有实例。在做了一些研究之后,似乎不可能对核心数据这样做,因为核心数据只支持边界框样式的查询,而不支持带块的谓词 例如,我有一类具有纬度和经度属性的组。给定纬度和经度(比如用户),获取给定纬度和经度6英里半径内的所有组 class Group{ var latitud

我有一个NSManagedObject类,它保存在核心数据中的SQLite数据库中。此对象具有持久的纬度和经度属性。我正在尝试创建一个NSFetchedRequestController,用于获取该类与用户之间一定距离内的所有实例。在做了一些研究之后,似乎不可能对核心数据这样做,因为核心数据只支持边界框样式的查询,而不支持带块的谓词

例如,我有一类具有纬度和经度属性的组。给定纬度和经度(比如用户),获取给定纬度和经度6英里半径内的所有组

class Group{
     var latitude: Float
     var longitude: Float
}
我想利用Core Data的R树索引对靠近我的用户的类实例的纬度和经度进行快速边界框查询。然后我想用更精确的谓词过滤结果,使用我自己的代码块查看哪些实例在我的用户当前位置内。这里是“边界框”查询

let请求:NSFetchRequest=Group.fetchRequest()
let(左上、右下)=边界框(中心:中心,半径:搜索半径)
设maxLat=topLeft.latitude
设minLon=topLeft.longitude
设minLat=bottomRight.latitude
设maxLon=bottomRight.longitude
let predicate=NSPredicate(格式:(%f<经度<%f)和(%f<纬度<%f)”,minLon,maxLon,minLat,maxLat)
request.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
}
let location:CLLocation=/*初始化CLLocation*/
let predicate=NSPredicate{(obj,)->Bool in
设object=obj as!组
设objLocation=CLLocation(纬度:Double(对象.纬度),经度:Double(对象.经度))
返回位置。距离(从:目标位置)<9656//6英里(米)
}
NSFetched results controller不允许带块的谓词。这两个回迁之间有很大的区别。第一个获取边界框中的所有组(minLat、minLon、maxLat和maxLat),后者获取给定半径圆中的所有组

然后我想使用NSFetchedRequestController在表中显示结果,并利用漂亮的自动更新功能。但当然,核心数据只支持边界框样式的查询,而不支持我需要的两步过滤方法。有合适的解决办法吗


如果核心数据不适合这种类型的使用,我愿意使用其他数据库。我看了一下YapDatabase,它看起来更灵活,包括R树索引,但我担心它没有得到很好的支持。Realm不支持R树索引。

问题有点不清楚-您是否表示希望通过半径在给定用户一定距离内找到其他用户?如果是这样的话,这与核心数据(对象图)有什么特别的关系?R-树有一个最小边界“框”,所以你能澄清问题是什么吗?您是否有一些您遇到困难的示例代码?也许,如果你能在问题中包含这一点,这将增加清晰度。@Jay我想还有很多悬而未决的问题。仅引用两点:1。)核心数据有一个R-TreeFetchIndex选项可用(当实际打开时,将生成所有SQLite R*树表)但不清楚NSPredicate必须是什么样子才能利用此功能2。)如果可以找到这样的NSPredicate,他希望使用自己的函数(过滤提取结果)使其更精确,并且该函数应作为“块”(或Swift中的闭包)实现@mark61 Core Data通过设置作为枚举的FetchIndex元素类型,提供了一个R树选项。也许通读文档会让你更清楚一点,所以我加入了链接。实际上并没有“打开”功能——如果设置了该属性,则获取请求将是r树,并且可以与NSPredicate一起使用
fetchRequest.predicate=predicate
@Jay选择NSFetchIndexElementType.rTree就是我打开开关的意思。对不起,如果它是含糊不清的。你有使用SQLite rTree索引表和核心数据的谓词格式字符串的例子吗?嘿@Ellight,我最终选择了完全不同的方向,使用Ruby on Rails构建自己的后端,让PostGIS数据库为我处理距离查询。不适合胆小的人。
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
}