ios中的位置时间戳准确度

时间:2017-01-12 06:36:41

标签: ios cllocationmanager ios10 cllocation

在分析iOS 10中的位置服务后,发现缓存行为存在一些不一致。

在定期时间(在我的情况下每20秒)获取位置会返回位置,但其时间戳不按时间顺序排列。这表明缓存位置可能存在问题。因此,如果您通过位置时间戳检查准确性,则还可以更好地保存以前的时间戳。这样您就可以决定是否可以使用所提取的位置。

下图来自我的控制台日志。在这里,我使用了格式“Lat Long: latitude_longitude | location_timestamp |现在: current_timestamp

highlighted rows have older timestamps

3 个答案:

答案 0 :(得分:2)

是的,有一段时间以最佳的准确度ios从缓存中获取位置,因此您需要避免这里的位置是准确定位的代码。

更新 “因为返回初始位置可能需要几秒钟,位置管理器通常会立即提供先前缓存的位置数据,然后在可用时提供更多最新的位置数据。因此,最好检查一下在采取任何行动之前任何位置对象的时间戳。“

参考:

https://developer.apple.com/reference/corelocation/cllocationmanager

注意:您可以改变设备的准确度,如ipod和ipad

//MARK: Location delgates
    func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation])
    {
        if locations.count > 0
        {
            let location = locations[locations.count-1]

            let maxAge:TimeInterval = 60;
            let requiredAccuracy:CLLocationAccuracy = 100;

            let locationIsValid:Bool = Date().timeIntervalSince(location.timestamp) < maxAge && location.horizontalAccuracy <= requiredAccuracy;
            if locationIsValid
            {
                NSLog(",,, location : %@",location);
                NSLog("valid locations.....");

            }
        }
    }

答案 1 :(得分:0)

是的,就像@chirag shah评论我们肯定需要做那个检查。我的建议是我们应该知道缓存技术已被修改。而且仅仅检查时间戳还不够,我们必须关注失败案例。这是目标C代码

-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations{

    CLLocation* location = [locations lastObject];
    NSDate* locationTimestamp = location.timestamp;
    NSTimeInterval cachedBefore = [locationTimestamp timeIntervalSinceNow];
    if (fabs(cachedBefore) < 60.0) {
        // Implement your code here
    }else{
        // Try again or wait for fetching location
    }
}

答案 2 :(得分:0)

这背后的问题是有时时间戳与位置不匹配!例如。旅行时你会突然记录速度&gt; 300km / h,精度最高。

我会对这些位置进行排序,如果不是太旧,我们只会选择最后一个:

func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {

        let sortedLocations = locations.sorted { (l1, l2) -> Bool in
            return l1.timestamp.compare(l2.timestamp) != .orderedDescending
        }

        if let newestLocation = sortedLocations.last{

            if Date().timeIntervalSince(newestLocation.timestamp) < 60{
                //TODO: Use the location
            }
        }
    }