代码之家  ›  专栏  ›  技术社区  ›  Phox

为NSOperationQueue创建Setter

  •  0
  • Phox  · 技术社区  · 7 年前

    我必须创建一个 NSOperationQueue 这是原子的。

    @property (atomic, strong) NSOperationQueue *queue;
    

    我有一个getter:

    - (NSOperationQueue *)queue {
      if (_queue == nil) {
        _queue = [NSOperationQueue mainQueue];
        [_queue setMaxConcurrentOperationCount:1];
      }
      return _queue;
    }
    

    但是Xcode说我必须创建一个setter。

    我这个案子的二传手该怎么做?我不知道。

    2 回复  |  直到 7 年前
        1
  •  2
  •   Rob    7 年前

    两个观察结果:

    1. 如果要定义自己的setter,它可能看起来像:

      - (void)setQueue:(NSOperationQueue *)queue {
          _queue = queue; 
      }
      

      请记住,如果同时实现两种访问器方法(setter和getter),则必须手动合成ivar,例如。

      @synthesize queue = _queue;
      

      在你的 @implementation ,因为编译器无法再安全地假设您需要特定名称的ivar。

    2. 你应该重新考虑是否应该 atomic nonatomic . 你的getter不是 原子的 (我的示例设定者也不是),所以您可能只想这样做 非原子的 . 存在 原子的 Programming with Objective-C: Properties are atomic by default ). 您通常不需要原子访问器方法,但如果需要,您会相应地更改这些实现以进行同步(例如 NSLock , @synchronized 指令、串行队列、读写器模式等)。

      非原子的 ,这也消除了编写自定义setter来附带自定义getter的需要。如果您为一个 原子的 属性,编译器无法合成相应的 原子的 setter,因为它无法知道如何将其setter与getter同步(因为可能有很多不同的同步机制)。但是如果你把你的财产 非原子的 ,在不需要同步的情况下,编译器可以为您合成简单的、未同步的setter,并且指示您实现setter的警告也将消失。

        2
  •  1
  •   gnasher729    7 年前

    首先,您将属性“queue”声明为读/写属性。这没有道理。你真的不希望每个人都分配到“队列”。

    其次,您将属性声明为“原子”。要么你仔细阅读了“原子”的功能,要么你只是相信我,它很少有用。手写的getter或setter总是非原子的。所以你有一个非原子的getter,因为属性本身是一个原子读/写属性,所以你有一个自动生成的setter,它是原子的。你不能把非原子的getter和原子setter结合起来,反之亦然。

    解决方法:将属性更改为非原子和只读。一个副作用是丢失了\u队列支持变量(如果实现了所有必需的访问器,则无法获得支持变量),因此您必须自己声明\u队列。