繁体   English   中英

目标C-行为常数

[英]Objective C - Constants with behaviour

我是Objective C的新手。我正在尝试定义与行为相关联的常量。 到目前为止,我已经完成了-

@interface Direction : NSObject {
     NSString *displayName;
}

-(id)initWithDisplayName:(NSString *)aName;

-(id)left; // returns West when North

-(id)right; // return East when North

@end

@implementation Direction

    -(id)initWithDisplayName:(NSString *)aName
    {
        if(self = [super init])
        {
            displayName = aName;
        }   
        return self;
    }

    -(id)left {};
    -(id)right {};

@end

Direction* North = [Direction initWithDisplayName:@"North"]; // error - initializer element is not constant.

这种方法导致指示的错误。 在目标C中是否有更好的方法可以做到这一点

简洁版本

存储方向的几何表示(使用矢量或简单角度),并动态计算方向名称。 要获得左右方向,请复制矢量并将其旋转±½π或±90°,以创建一个新方向并将其返回。 如果只有90度转弯,则可以使用点{0,1},并切换方向,也可以在进行操作时取反。 ({0,1}是北; {1,0}是东,{-1,-0}是西,{-0,-1}是南,因此,如果使用此方法,则必须具有一些额外的代码来确定何时取反,何时不取反。)

长版

问题是函数以外的变量在编译时初始化。 自然,这意味着您无法调用函数来对其进行初始化。 为此,您需要执行以下操作(尽管您不应该这样做,请参见下文):

// Direction.h

extern Direction *north;

// Direction.m

Direction *north = nil;

+ (void)initialize {
  north = [[Direction alloc] initWithDisplayName:@"North"];
}

但是,这是处理事情的几乎完全糟糕的方法。 想要做的如下:

// Direction.h


@interface Direction (ConstantDirections)

+ (Direction *)north;
// etc...

@end

// Direction.m

+ (Direction *)north {
  static Direction *northDirection = nil;
  if (!northDirection) {
    // assume that ConstantDirection is a subclass of
    // Direction that prevents releases etc.
    northDirection = [[ConstantDirection alloc] initWithDisplayName:@"North"];
  }
  return northDirection.
}

这将防止该方向的其他用户(大多数情况下)从事恶意活动。

PS: North是一个非常奇怪的词,特别是当您多次输入时。 :P

编辑:关于使用基本方向作为单独对象的一些说明。

在实践中,您的Direction类可能看起来像这样:

@interface Direction : NSObject <NSCopying,NSCoding> {
  NSString *displayName;

  NSPoint offset;
  // XOR
  NSInteger northOffset;
  NSInteger eastOffset;
  // XOR
  CGFloat theta;
}

@property (copy) NSString *displayName;
@property (readonly) NSPoint offset;

+ (Direction *)north;
+ (Direction *)east;
+ (Direction *)west;
+ (Direction *)south;

- (id)initWithOffset:(NSPoint)offset;

@end

为了便于讨论,我们将假设第一个。

在这种情况下,Direction.m文件将包含以下内容。

@implementation Direction 

+ (Direction *)north {
  static Direction *northDirection = nil;
  if (!northDirection) {
    // assume that ConstantDirection is a subclass of
    // Direction that prevents releases etc.
    northDirection = [[ConstantDirection alloc] initWithOffset:NSMakePoint(0,DIRECTION_LARGE_OFFSET)];
    northDirection.displayName = @"North";
  }
  return northDirection.
}

@end

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM