我目前正在开发一个 iPhone 应用程序,并且我有一个来自第三方的库,它具有异步行为,但我想用我自己的类进行包装并使其看起来是同步的。
这个库中的中心类,我们称之为 Connection 类,有几个函数,当调用委托类的实例上的方法时,它们的最终结果会被解析。我想要做的是包装这个类和委托,使它看起来是同步的而不是异步的。如果我在 Java 中执行此操作,我会使用 FutureTask 或 CountdownLatch 或只是 join()。但我不确定在 Objective C 中执行此操作的最佳方法。
我首先创建了一个符合上述委托协议的 NSThread 扩展 NFCThread。这个想法是我将初始化和 NFCThread,将 NFCThread 实例传递给 Connection 的 setDelegate 方法,启动线程,然后在 Connection 上调用异步方法。我的期望是调用 NFCThread 实例上的三个委托方法之一,最终导致线程退出。
为了模拟加入,我做了以下事情。我在 NFCThread 中添加了一个 NSConditionalLock:
joinLock = [[NSConditionLock alloc] initWithCondition:NO];
调用 Connection 的代码如下所示:
NFCThread *t = [[NFCThread alloc] init];
[connection setDelegate:t];
[t start];
[connection openSession];
// Process errors, etc...
[t.joinLock lockWhenCondition:YES];
[t.joinLock unlock];
[t release];
[connection setDelegate:nil];
委托的协议具有三种方法。在 NFCThread 中,我实现了每个方法,如下所示:
- (void)didReceiveMessage:(CommandType)cmdType
data:(NSString *)responseData
length:(NSInteger)length {
NSLog(@"didReceiveMessage");
// Do something with data and cmdType...
[joinLock lock];
[joinLock unlockWithCondition:YES];
callBackInvoked = YES;
}
我重载了 NFCThread 的 main 方法,使它不断循环。像这样的东西:
while (!callBackInvoked) { ; }
我发现这并不是一个好主意,因为它会导致 CPU 使用率飙升。因此,我尝试使用我在此站点上找到的一些示例中的运行循环:
NSRunLoop *runLoop = [NSRunLoop currentRunLoop];
[runLoop addPort:[NSMachPort port] forMode:NSDefaultRunLoopMode];
while (!callBackInvoked) {
[runLoop runMode:NSDefaultRunLoopMode beforeDate:[NSDate distantFuture]];
}
在我的两个实现中,主线程总是被阻塞,并且似乎没有调用任何委托方法。但是,我知道该库运行正常,并且通常调用委托方法。
我觉得我在这里遗漏了一些明显的东西。非常感谢任何帮助。
富有的