我正在开发一个计算用户行进距离的应用程序。我正在使用CLLocationManager类来执行此操作,但我最初获取缓存数据,并且距离变量也以突然的速率增加。请帮帮我...我使用了以下代码......
注意:距离是静态变量。这里
- (void)viewDidLoad {
[super viewDidLoad];
//bestEffortAtLocation = nil;
oldLocat = [[CLLocation alloc]init];
newLocat = [[CLLocation alloc]init];
locationManager =[[CLLocationManager alloc]init];
locationManager.delegate = self;
locationManager.distanceFilter = kCLDistanceFilterNone;
locationManager.desiredAccuracy = kCLLocationAccuracyBest;
[locationManager startUpdatingLocation];
}
- (void)locationManager:(CLLocationManager *)manager
didUpdateToLocation:(CLLocation *)newLocation
fromLocation:(CLLocation *)oldLocation{
// test that the horizontal accuracy does not indicate an invalid measurement
if (newLocation.horizontalAccuracy < 0) return;
NSLog(@"accuracy %d",newLocation.horizontalAccuracy);
// test the age of the location measurement to determine if the measurement is cached
// in most cases you will not want to rely on cached measurements
NSTimeInterval locationAge = -[newLocation.timestamp timeIntervalSinceNow];
//NSLog(@"time %d",locationAge);
if (locationAge > 5.0) return;
self.oldLocat = oldLocation;
self.newLocat = newLocation;
double latDegrees = newLocation.coordinate.latitude;
NSString *lat = [NSString stringWithFormat:@"%1.5f°",latDegrees];
latLabel.text = lat;
double longDegrees = newLocation.coordinate.longitude;
NSString *longt = [NSString stringWithFormat:@"%1.5f°",longDegrees];
longLabel.text = longt;
[self computeDistanceFrom:oldLocat tO:newLocat];
}
-(void)computeDistanceFrom:(CLLocation *)oldL tO:(CLLocation *)newL
{
NSLog(@"oldd %@",oldL);
NSLog(@"new %@",newL);
distance = distance + [oldL getDistanceFrom:newL];
NSLog(@"distance %f",distance);
}
控制台显示以下数据.......
准确度0 oldd(null)new&lt; +28.62114850,+ 77.37001021&gt; +/- 80.00米 (速度-1.00 mps /当然-1.00)@ 2010-06-22 19:21:59 +0530距离 0.000000
准确度0 oldd&lt; +28.62114850,+ 77.37001021&gt; +/- 80.00米(速度-1.00 mps / course -1.00)@ 2010-06-22 19:21:59 +0530 new&lt; +28.61670485, + 77.37068155&GT; +/- 80.00米(速度-1.00 mps /航向-1.00)@ 2010-06-22 19:22:00 +0530 距离498.211345
准确度0 oldd&lt; +28.61670485,+ 77.37068155&gt; +/- 80.00米(速度-1.00 mps / course -1.00)@ 2010-06-22 19:22:00 +0530 new&lt; +28.62112748, + 77.36998540&GT; +/- 80.00m(速度-1.00 mps /航向-1.00)@ 2010-06-22 19:23:02 +0530距离994.432508
答案 0 :(得分:7)
最初从之前获取缓存位置是正常的。您可以通过查看timestamp的CLLocation来忽略较旧的缓存数据。
您打印的准确度不正确,使用%f而非%d,类型为double而不是int。
GPS首次启动时位置可能会快速变化,因为您从单元格三角测量中获得的精度较低,然后当您获得GPS采集时,您将获得更高精度的位置。那些距离很远(1000米),看起来你在几秒钟内移动了很远,但只是准确性发生了变化。
请勿使用精度差异非常大的两个位置来计算行进距离。
编辑添加了代码示例,如何忽略旧的位置数据。你决定要忽略多久,我在这里用了60秒:
- (void)locationManager:(CLLocationManager *)manager
didUpdateToLocation:(CLLocation *)newLocation
fromLocation:(CLLocation *)oldLocation {
NSTimeInterval ageInSeconds = -[newLocation.timestamp timeIntervalSinceNow];
if (ageInSeconds > 60.0) return; // data is too long ago, don't use it
// process newLocation
...
}
答案 1 :(得分:2)
您已确保您的位置更新时间不到五秒钟。这就是这行代码的作用:
if (locationAge > 5.0) return;
正如progrmr所述,这里的关键问题几乎可以肯定是你依赖于初始的位置估计值,这些估计值的准确度较低,因此位置看起来会快速移动,因为它可以更好地修复您的位置。您需要做的是首先确保只有在准确的初始位置修复时才设置oldLocation,然后仅将newLocations与oldLocation进行比较(如果它们也具有可接受的分辨率)。
例如,你可以这样:
- (void)locationManager:(CLLocationManager *)manager
didUpdateToLocation:(CLLocation *)newLocation
fromLocation:(CLLocation *)oldLocation{
// Ignore location updates that are less than 10m accuracy, or where the horizontalAccuracy < 0
// which indicates an invalid measurement.
NSLog(@"New location accuracy %.0fm", newLocation.horizontalAccuracy);
if ((newLocation.horizontalAccuracy < 0) || (newLocation.horizontalAccuracy > 10)) return;
// Ignore location updates that are more than five seconds old, to avoid responding to
// cached measurements.
NSTimeInterval locationAge = -[newLocation.timestamp timeIntervalSinceNow];
if (locationAge > 5) return;
if (self.oldLocat == NULL)
{
// For the first acceptable measurement, simply set oldLocat and exit.
self.oldLocat = newLocation;
return;
}
// A second location has been identified. Calculate distance travelled.
// Do not set self.oldLocat from the oldLocation provided in this update, as we wish to
// use the last place we calculated distance from, not merely the last place that was
// provided in a location update.
CLLocationDistance distance = [newLocation distanceFromLocation:self.oldLocat];
NSLog(@"Distance: %.0fm", distance);
// This new location is now our old location.
self.oldLocat = newLocation;
}
注意上面的代码,你不需要方法computeDistanceFrom:tO:,并且实际上并不需要属性self.newLocat,至少在这部分代码中。