-1

我正在关注 Ray Wenderlich 网站上的教程,我试图理解这段代码,它具有 nsarray 只读和 nsmutableble 数组,名称相同但可写。还有什么是使用 _(underscore)property 与设置属性和使用 self.x 的原因 这是代码:这是来自网站

对接会服务器.h

@interface MatchmakingServer : NSObject <GKSessionDelegate>

@property (nonatomic, assign) int maxClients;
@property (nonatomic, strong, readonly) NSArray *connectedClients;
@property (nonatomic, strong, readonly) GKSession *session;

- (void)startAcceptingConnectionsForSessionID:(NSString *)sessionID;

@end

婚介服务器.m

#import "MatchmakingServer.h"

@implementation MatchmakingServer
{
    NSMutableArray *_connectedClients;
}

@synthesize maxClients = _maxClients;
@synthesize session = _session;

- (void)startAcceptingConnectionsForSessionID:(NSString *)sessionID
{
    _connectedClients = [NSMutableArray arrayWithCapacity:self.maxClients];

    _session = [[GKSession alloc] initWithSessionID:sessionID displayName:nil sessionMode:GKSessionModeServer];
    _session.delegate = self;
    _session.available = YES;
}

我正在做这样的事情

婚介服务器.h

@interface zvMatchMakingServer : NSObject <GKSessionDelegate>

@property (nonatomic, assign) int maxClients;
@property (nonatomic, strong, readonly) NSArray *connectedClients;
@property (nonatomic, strong, readonly) GKSession *session;

- (void)startAcceptingConnectionsForSessionID:(NSString *)sessionID;


@end

婚介服务器.m

@interface zvMatchMakingServer()

@property (nonatomic,strong) NSMutableArray *connectedClients;
@property (nonatomic, strong) GKSession *session;

@end

@implementation zvMatchMakingServer


-(NSArray *)connectedClients
{
    return self.connectedClients;
}

-(void)startAcceptingConnectionsForSessionID:(NSString *)sessionID
{
    self.connectedClients = [[NSMutableArray alloc]initWithCapacity:self.maxClients];
    self.session = [[GKSession alloc]initWithSessionID:sessionID displayName:nil sessionMode:GKSessionModeServer];

}

我在做什么基本上是一样的,否则它不会工作。谢谢!

4

1 回答 1

1

我将尝试解释 Ray 的代码中发生了什么:

他声明了一个属性:

@property (nonatomic, strong, readonly) NSArray *connectedClients;

(我认为这是 iOS 6 之前的版本,因为在 iOS 6 中,Apple 改变了属性生成 iVar 的方式。)

此属性使编译器自动生成 iVar NSArray *connectedClients。代码中未使用此 iVar。_connectedClients相反,他声明了一个名为type的新(私有)iVar NSMutableArray。请注意,他不会合成该属性的访问器。他自己编写访问器,而不是返回由属性 (connectedClients) 生成的 iVar,而是返回他自己的 iVar (_connectedClients):

- (NSArray *)connectedClients
{
    return _connectedClients;
}

因为NSMutableArray是一个子类,NSArray所以这样做没有问题。

您正在做的是试图将财产重新声明@property (nonatomic,strong) NSMutableArray *connectedClients;为私有财产,这是不允许的。仔细将您的代码与 Ray 的代码进行比较,然后您会发现不同之处。

至于下划线:

这只是许多人用来命名他们的 iVar 的惯例。它没有语义意义。事实上,Apple 将“自动生成”iVar 的名称更改为也使用下划线。

iOS 6 之前的一个属性

@property (...) SomeClass *name;

生成了一个名为name. 在 iOS 6 中,相同的属性会生成一个名为_name. 同样在 iOS 6 中,您不再需要添加该@synthesize行。

使用下划线为 iVar 的名称添加前缀很方便,因为如果您想覆盖自动生成的访问器,自动补全建议这样做:

- (void)setName:(SomeClass *)name

如果您的 iVar 也被命名name,则参数name将在访问器实现中隐藏 iVar,因此您必须更改参数的名称。如果您通过使用@synthesize name = _name参数重命名您的 iVarname不再隐藏它,您可以使用自动完成生成的访问器代码。

- (void)setName:(SomeClass *)name
{
    //maybe release the old value and retain the new one if you're not using ARC and weather it's a retained property or not. 
   _name = name;
}
于 2012-10-28T17:39:45.500 回答