iphone - @synthesize 干扰继承

标签 iphone objective-c

FINAL EDIT

The solution to all life's problems: enter image description here

Switching xcode's "Compiler Version" setting to "LLVM compiler 2.0" solves this issue, many thanks to Firoze Lafeer for the concerted, constructive assistance!

目的是通过子类化 NSObject 和 UIViewController 来在我的所有类中构建一些非常基本的功能,以获取应用程序委托(delegate),稍微扩展 viewDidAppear 机制等。我有一个看起来像这样的基类(仅包含相关行):

@interface PHView : UIViewController {
    id<PHAppDelegate> appDelegate;
}
-(id)init;
//some other method prototypes
@property (nonatomic, retain) id delegate;
@end

@implementation PHView
@synthesize delegate;

-(id)init {
    self = [super init];
    appDelegate = (id<PHAppDelegate>)[[UIApplication sharedApplication] delegate];
    visible = FALSE;
    initialized = FALSE;
    return self;
}
    //some other methods
@end

编辑我应该在这里提到属性“delegate”并不意味着指向ivar“appDelegate”或任何东西......我只是将其保留以说明这个父类(super class)使用@synthesize 。由于这不是相关的用法,我认为这并不重要,但我不会说我知道这一点。

子类的接口(interface):

@interface PinMap : PHView <MKMapViewDelegate> {
//@interface PinMap : UIViewController <MKMapViewDelegate> {
//    NSObject<PHAppDelegate>* appDelegate;
}
-(id)init;
-(void)zoomToUser;
@property (nonatomic, retain) IBOutlet MKMapView* map;
@end

编译:

@implementation PinMap
//@synthesize map;

-(PinMap*) init{
    self = [super init];
    //appDelegate = (NSObject<PHAppDelegate>*)[[UIApplication sharedApplication] delegate];    
    return self;
}

-(void)zoomToUser {
    //MKCoordinateRegion region = map.region;
    MKCoordinateRegion region = MKCoordinateRegionMake(CLLocationCoordinate2DMake((CLLocationDegrees)300, (CLLocationDegrees)300), MKCoordinateSpanMake((CLLocationDegrees)20,(CLLocationDegrees)20)); //random region
    region.center = [[appDelegate location] coordinate];
    region.span.longitudeDelta /= 50.0;
    region.span.latitudeDelta /= 50.0;
//    [map setRegion:region animated:NO];
}

这不会编译:

@implementation PinMap
@synthesize map;

-(PinMap*) init{
    self = [super init];
    //appDelegate = (NSObject<PHAppDelegate>*)[[UIApplication sharedApplication] delegate];    
    return self;
}

-(void)zoomToUser {
    MKCoordinateRegion region = map.region;
    //MKCoordinateRegion region = MKCoordinateRegionMake(CLLocationCoordinate2DMake((CLLocationDegrees)300, (CLLocationDegrees)300), MKCoordinateSpanMake((CLLocationDegrees)20,(CLLocationDegrees)20)); //random region
    region.center = [[appDelegate location] coordinate]; // <-- ERROR HERE
    region.span.longitudeDelta /= 50.0;
    region.span.latitudeDelta /= 50.0;
    [map setRegion:region animated:NO];
}

在标记的位置,我得到“”“'appDelegate'未声明(在此函数中首次使用)”“”我的第一步是清理,重新启动并再次清理(本周使用该过程修复了三个错误)以及何时这不起作用,我开始尝试一些有意义的事情,最终尝试一些没有意义的事情。

以下内容确实可以编译(并运行),但老实说我不明白为什么:

@interface PinMap : PHView <MKMapViewDelegate> {
//@interface PinMap : UIViewController <MKMapViewDelegate> {
    //NSObject<PHAppDelegate>* appDelegate;
    MKMapView* _map;
}
-(id)init;
-(void)zoomToUser;
@property (nonatomic, retain) IBOutlet MKMapView* map;
@end

@implementation PinMap
@synthesize map=_map;

-(PinMap*) init{
    self = [super init];
    //appDelegate = (NSObject<PHAppDelegate>*)[[UIApplication sharedApplication] delegate];    
    return self;
}

-(void)zoomToUser {
    MKCoordinateRegion region = self.map.region;
    //MKCoordinateRegion region = MKCoordinateRegionMake(CLLocationCoordinate2DMake((CLLocationDegrees)300, (CLLocationDegrees)300), MKCoordinateSpanMake((CLLocationDegrees)20,(CLLocationDegrees)20)); //random region
    region.center = [[appDelegate location] coordinate];
    region.span.longitudeDelta /= 50.0;
    region.span.latitudeDelta /= 50.0;
    [self.map setRegion:region animated:NO];
}

在此装饰中,它将响应“self.map”,但认为“map”未声明。

编辑“ self ”要求现在对我来说是有意义的,但消失/重新出现的“appDelegate”ivar才是我真正担心的。抱歉,如果之前不清楚。但说真的,这是怎么回事?

最佳答案

首先,PinMap 没有名为“map”的实例变量 (ivar)。

它有一个名为“map”的属性,您可以像这样访问它:

region = self.map.region;

或者它有一个名为 _map 的 ivar。所以你可以这样做:

region = _map.region;

但推荐前者。您创建了一个属性,因此您可能想使用它(在 initXXX 和 dealloc 之外)

编辑

此外,UIViewController 的指定初始化程序是 initWithNibName:bundle:

因此,请确保您是否将 UIViewController 子类化并调用其指定的初始值设定项。

再次编辑

在您的评论中的这些情况下,您可能有一个 ivar 和一个同名的属性。如果你只是做@synthesize propname,这就是你得到的。但在本例中,您执行了 @synthesize map = _map。

值得花时间了解何时直接访问 ivar 与属性。否则很多事情就没有意义,并且会发生其他错误。要访问该属性,您必须执行“self.propertyName”(或 [self propertyName] 或 [self setPropertyName:something])

如果您不使用 self,则您不会使用 getter/setter(这通常是一件坏事,例如,如果您的 getter/setter 正在为您执行内存管理或初始化)。如果您不打算使用该属性,则还必须使用实际的 ivar 名称。

再次编辑

我发现更改编译器有帮助。那么我建议两件事:仔细检查所有 @synthesize 语句,以确保您没有要求编译器在父类(super class)中已经存在的子类中合成 ivar。当您解决这个问题时,我建议您将 ivars 命名为“variable_”或“_variable”,以便您可以轻松查看在何处使用 ivar 与该属性。

更重要的是,您确实应该升级到 LLVM 3.0,它包含在 Xcode 4.2.1 中。

关于iphone - @synthesize 干扰继承,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8349609/

相关文章:

iphone - UILocalNotification - 通知不显示

objective-c - 在 NSString 中显示时如何使 CGFloat 值更短?

ios - NSFetchRequest "returnsDistinctResults"似乎被忽略了

iphone - 如何在ARC环境中将Parser Delegate设置为Self?

iphone - 自定义 ABPeoplePickerNavigationController

ios - 设置 MPMoviePlayerController 的方向

iphone - 在循环中动态添加 UILabel

objective-c - Cocoa 有没有办法知道 NSTextField 是否脏了?如果已经编辑过?

ios - 如何在 Objective-C 中过滤自定义对象

iphone - AFNetworking 需要 60 秒才能返回 401 状态代码?