Objective C共享readonly类的实例

时间:2013-04-17 14:35:22

标签: objective-c

我想在Objective C中创建一个类的只读实例。我有一个向量类,基本上浮动x和y位置以及一些方法。在很多情况下我需要一个(0,0) - 向量,所以我想的是每次我有一个共享的零向量而不是分配一个新的,这样的事情:

// Don't want to do this all the time (allocate new vector)
compare(v, [[Vector alloc] initWithCartesian:0:0]);

// Want to do this instead (use a shared vector, only allocate once)
compare(v, [Vector zeroVector]);

// My attempt so far
+ (Vector *)zeroVector {
    static Vector *sharedZeroVector = nil;
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        sharedZeroVector = [[self alloc] initWithCartesian:0:0];
    });
    return sharedZeroVector;
}

// The problem
v.x = 3;

这样可以正常工作,除了零矢量不是只读,这感觉有点傻。作为一个说明,我想提一下,这更像是一个想要知道如何的问题,而不是一个实际的问题,我不知道它是否会产生一些实际的差异。

3 个答案:

答案 0 :(得分:5)

常见的解决方案是让所有实例都不可变(请参阅NSNumberNSDecimalNumber等),可能有第二个可变类(NSString vs NSMutableString或{{1 }} vs NSArray)。

答案 1 :(得分:4)

取决于标准向量应如何工作。如果你不想通过属性设置x和y,你可以只读它们:

@property (nonatomic, readonly) NSInteger x;
@property (nonatomic, readonly) NSInteger y;

如果你的某些矢量应该是readwrite,你可以创建一个只读类Vector并派生一个MutableVector类:

@interface Vector : NSObject
  @property (nonatomic, readonly) NSInteger x;
  @property (nonatomic, readonly) NSInteger y;
@end

@interface MutableVector : Vector
  @property (nonatomic) NSInteger x;
  @property (nonatomic) NSInteger y;
@end

然后,您将使用Vector for zeroVector和MutableVector for all others。

答案 2 :(得分:0)

您是否只想阻止其他类更改此类字段?

将它们标记为@private并且(如Sulthan所写),确保您的-zeroVector方法返回的类是不可变的(可能是Vector的不可变子类),即没有允许其他代码更改其状态的方法。

另请参阅related question about Obj-C private fields