首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >使用CLLocationManager计算准确的步行/跑步总距离有困难

使用CLLocationManager计算准确的步行/跑步总距离有困难
EN

Stack Overflow用户
提问于 2012-01-09 00:15:20
回答 2查看 7.4K关注 0票数 16

我正在尝试构建一个iOS应用程序,它可以显示跑步或步行时的总里程。我已经一遍又一遍地阅读了我能找到的所有文档,但我在想出一个准确的总距离时遇到了麻烦。

与Nike+ GPS或RunKeeper相比,我的应用程序总是报告更短的距离。他们一开始会报告相同的,但随着我的不断移动,我的应用程序相对于其他运行中的应用程序的价值逐渐漂移。

例如,如果我步行.3公里(由我的汽车里程表验证),Nike+和RunKeeper每次都会报告~.3公里,但我的应用程序会报告~.13公里。newLocation.horizontalAccuracy始终为5.0或10.0。

这是我正在使用的代码。我是不是漏掉了什么明显的东西?有什么想法我可以改进这一点,以获得更准确的读数?

代码语言:javascript
复制
#define kDistanceCalculationInterval 10 // the interval (seconds) at which we calculate the user's distance
#define kNumLocationHistoriesToKeep 5 // the number of locations to store in history so that we can look back at them and determine which is most accurate
#define kValidLocationHistoryDeltaInterval 3 // the maximum valid age in seconds of a location stored in the location history
#define kMinLocationsNeededToUpdateDistance 3 // the number of locations needed in history before we will even update the current distance
#define kRequiredHorizontalAccuracy 40.0f // the required accuracy in meters for a location.  anything above this number will be discarded

- (id)init {
    if ((self = [super init])) {
        if ([CLLocationManager locationServicesEnabled]) {
            self.locationManager = [[CLLocationManager alloc] init];
            self.locationManager.delegate = self;
            self.locationManager.desiredAccuracy = kCLLocationAccuracyBestForNavigation;
            self.locationManager.distanceFilter = 5; // specified in meters
        }

        self.locationHistory = [NSMutableArray arrayWithCapacity:kNumLocationHistoriesToKeep];
    }

    return self;
}

- (void)locationManager:(CLLocationManager *)manager didUpdateToLocation:(CLLocation *)newLocation fromLocation:(CLLocation *)oldLocation {
    // since the oldLocation might be from some previous use of core location, we need to make sure we're getting data from this run
    if (oldLocation == nil) return;
    BOOL isStaleLocation = [oldLocation.timestamp compare:self.startTimestamp] == NSOrderedAscending;

    [self.delegate locationManagerDebugText:[NSString stringWithFormat:@"accuracy: %.2f", newLocation.horizontalAccuracy]];

    if (!isStaleLocation && newLocation.horizontalAccuracy >= 0.0f && newLocation.horizontalAccuracy < kRequiredHorizontalAccuracy) {

        [self.locationHistory addObject:newLocation];
        if ([self.locationHistory count] > kNumLocationHistoriesToKeep) {
            [self.locationHistory removeObjectAtIndex:0];
        }

        BOOL canUpdateDistance = NO;
        if ([self.locationHistory count] >= kMinLocationsNeededToUpdateDistance) {
            canUpdateDistance = YES;
        }

        if ([NSDate timeIntervalSinceReferenceDate] - self.lastDistanceCalculation > kDistanceCalculationInterval) {
            self.lastDistanceCalculation = [NSDate timeIntervalSinceReferenceDate];

            CLLocation *lastLocation = (self.lastRecordedLocation != nil) ? self.lastRecordedLocation : oldLocation;

            CLLocation *bestLocation = nil;
            CGFloat bestAccuracy = kRequiredHorizontalAccuracy;
            for (CLLocation *location in self.locationHistory) {
                if ([NSDate timeIntervalSinceReferenceDate] - [location.timestamp timeIntervalSinceReferenceDate] <= kValidLocationHistoryDeltaInterval) {
                    if (location.horizontalAccuracy < bestAccuracy && location != lastLocation) {
                        bestAccuracy = location.horizontalAccuracy;
                        bestLocation = location;
                    }
                }
            }
            if (bestLocation == nil) bestLocation = newLocation;

            CLLocationDistance distance = [bestLocation distanceFromLocation:lastLocation];
            if (canUpdateDistance) self.totalDistance += distance;
            self.lastRecordedLocation = bestLocation;
        }
    }
}
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2012-01-09 22:28:06

事实证明,我在上面发布的代码工作得很好。问题恰好出现在我的应用程序的另一个部分。我意外地将距离从米转换为英里,而不是从米转换为公里。糟了!

无论如何,希望我的帖子仍然有一些优点,因为我觉得这是一个很好的例子,说明了如何使用Core Location跟踪用户的距离。

票数 10
EN

Stack Overflow用户

发布于 2012-01-09 02:15:06

您可能将kRequiredHorizontalAccuracy设置得太低了。如果历史记录中没有accuracy < kRequiredHorizontalAccuracy的位置,则忽略所有这些点并将距离添加0。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/8779074

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档