【问题标题】:CLLocationManager delegate not called [duplicate]未调用 CLLocationManager 委托 [重复]
【发布时间】:2011-11-29 14:37:03
【问题描述】:

我在设备上使用CLLocationManager 并且没有调用委托方法。这是我的代码(我可以看到该类也没有被释放):

#import <Foundation/Foundation.h>
#import <CoreLocation/CoreLocation.h>

@interface CurrentLocation : NSObject <CLLocationManagerDelegate> {
    CLLocationManager *locationManager;

}
@property (nonatomic, retain) CLLocationManager *locationManager;  

@end

#import "CurrentLocation.h"
#import "SBJson.h"
@implementation CurrentLocation
@synthesize locationManager;

- (id)init
{
    self = [super init];
    if (self) {
        NSLog(@"Initialized");
        locationManager = [[[CLLocationManager alloc] init] autorelease];
        locationManager.delegate = self;
        [locationManager startUpdatingLocation];
        BOOL enable = [CLLocationManager locationServicesEnabled];
        NSLog(@"%@", enable? @"Enabled" : @"Not Enabled");
    }

    return self;
}

- (void)locationManager:(CLLocationManager *)manager
    didUpdateToLocation:(CLLocation *)newLocation
           fromLocation:(CLLocation *)oldLocation {
    NSLog(@"A");
    NSString *stringURL = [NSString stringWithFormat:@"http://maps.googleapis.com/maps/api/geocode/json?latlng=%f,%f&sensor=true", newLocation.coordinate.latitude, newLocation.coordinate.longitude];
    NSLog(@"%@", stringURL);

    NSURL *url = [NSURL URLWithString:stringURL];

    NSData *data = [NSURLConnection sendSynchronousRequest:[NSURLRequest requestWithURL:url] returningResponse:nil error:nil];

    SBJsonParser *parser = [[SBJsonParser alloc] init];
    NSDictionary *dict = [parser objectWithData:data];
    NSLog(@"%@", dict);
}

- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error {
    NSLog(@"B");
}

- (void)dealloc {
    NSLog(@"Dealloc called");
    [super dealloc];
    [locationManager release];
}

@end

在日志中,我看到:

2011-10-02 19:49:04.095 DixieMatTracker[1404:707] Initialized
2011-10-02 19:49:04.109 DixieMatTracker[1404:707] Enabled

我做错了什么? 谢谢

【问题讨论】:

  • locationManager 属性是如何定义的?
  • 不太可能有所作为,但我见过更奇怪的事情。放置 self.locationManager (访问属性)。没有 self,它会访问支持变量,而不保留(因为您已经自动释放)。
  • @PragmaOnce 是assign,retain,什么?尝试改用self.locationManager。 @Daryl Teo 我同意,这很可能是问题,因为 locationManager 将被自动释放。
  • [super dealloc] 应该在您的自定义 dealloc 实现结束时调用,而不是首先调用。

标签: objective-c ios cocoa-touch cllocationmanager


【解决方案1】:

我建议您检查 CLLocationManager 实例上的内存管理。

这样写:

#import "CurrentLocation.h"
#import "SBJson.h"
@implementation CurrentLocation
@synthesize locationManager;

- (id)init
{
    self = [super init];
    if (self) {
        NSLog(@"Initialized");
        locationManager = [[CLLocationManager alloc] init];
        locationManager.delegate = self;
        [locationManager startUpdatingLocation];
        BOOL enable = [CLLocationManager locationServicesEnabled];
        NSLog(@"%@", enable? @"Enabled" : @"Not Enabled");
    }

    return self;
}

- (void)locationManager:(CLLocationManager *)manager
    didUpdateToLocation:(CLLocation *)newLocation
           fromLocation:(CLLocation *)oldLocation {
    NSLog(@"A");
    NSString *stringURL = [NSString stringWithFormat:@"http://maps.googleapis.com/maps/api/geocode/json?latlng=%f,%f&sensor=true", newLocation.coordinate.latitude, newLocation.coordinate.longitude];
    NSLog(@"%@", stringURL);

    NSURL *url = [NSURL URLWithString:stringURL];

    NSData *data = [NSURLConnection sendSynchronousRequest:[NSURLRequest requestWithURL:url] returningResponse:nil error:nil];

    SBJsonParser *parser = [[SBJsonParser alloc] init];
    NSDictionary *dict = [parser objectWithData:data];
    NSLog(@"%@", dict);
}

- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error {
    NSLog(@"B");
}

- (void)dealloc {
    NSLog(@"Dealloc called");
    [super dealloc];
    [locationManager release];
}

@end

委托没有被调用,因为 CLLocationManager 对象在它可以提供对位置请求的响应之前被释放。 这是由代码中的自动释放引起的。

除此之外 - 如果使用了 autorelease,那么在 dealloc 中手动释放它是错误的。这可能会导致意外崩溃。

上面的解决方案是“手动”在init 中分配一个CLLocationManager 并在dealloc 中释放它。

【讨论】:

  • 哇。那行得通。仍然不明白为什么 CLLocationManager 实例被释放......我正在自动释放,然后使用原告保留它。无论如何,非常感谢。
  • 这并不能解决根本问题:该属性未被使用。
  • 未要求使用该属性。顺便说一句,如果该属性被定义为保留并且已使用 self.locationManager 正确访问,则会发生这种情况
【解决方案2】:

您使用的是locationManager ivar,而不是属性;这意味着 CLLocationManager 不会被保留,并且会在您自动释放它时被释放。使用self.locationManager:

self.locationManager = [[[CLLocationManager alloc] init] autorelease];

【讨论】:

  • 不敢相信我没听懂... :(。谢谢。
【解决方案3】:

在我的情况下,这是因为我的设备无法确定位置 - 当我待在室内时,GPS 信号不可用且 wi-fi 也断开连接,因此位置管理器无法接收任何位置数据,并且从未呼叫过委托人.

一旦我连接了 wi-fi,它就可以工作了(我想在这种情况下搬到户外也应该可以解决问题,但有时这不是很方便的方式 :))

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2016-05-07
    • 1970-01-01
    • 1970-01-01
    • 2016-05-12
    • 2014-09-20
    • 1970-01-01
    • 2013-12-03
    • 2011-03-12
    相关资源
    最近更新 更多