Parser 中GCD的使用(9)

2020-01-18  本文已影响0人  老猫_2017

PFReachability.m 网络监控

// 并行队列
_synchronizationQueue = dispatch_queue_create("com.parse.reachability", DISPATCH_QUEUE_CONCURRENT);

// 屏障独写
- (void)addListener:(id<PFReachabilityListener>)listener {
    PFWeakValue *value = [PFWeakValue valueWithWeakObject:listener];
    dispatch_barrier_sync(_synchronizationQueue, ^{
        [self->_listenersArray addObject:value];
    });
}

// 屏障独写
- (void)removeListener:(id<PFReachabilityListener>)listener {
    @weakify(listener);
    dispatch_barrier_sync(_synchronizationQueue, ^{
        @strongify(listener);
        [self->_listenersArray filterUsingPredicate:[NSPredicate predicateWithBlock:^BOOL(id evaluatedObject, NSDictionary *bindings) {
            id weakObject = [evaluatedObject weakObject];
            return !(weakObject == nil || weakObject == listener);
        }]];
    });
}

- (void)removeAllListeners {
    dispatch_barrier_sync(_synchronizationQueue, ^{
        [self->_listenersArray removeAllObjects];
    });
}
// 异步并发执行
- (void)_notifyAllListeners {
    @weakify(self);
    dispatch_async(_synchronizationQueue, ^{
        @strongify(self);
        PFReachabilityState state = [[self class] _reachabilityStateForFlags:self->_flags];
        for (PFWeakValue *value in self->_listenersArray) {
            [value.weakObject reachability:self didChangeReachabilityState:state];
        }

        dispatch_barrier_async(self->_synchronizationQueue, ^{
            [self->_listenersArray filterUsingPredicate:[NSPredicate predicateWithFormat:@"SELF.weakObject != nil"]];
        });
    });
}

// 异步并发独写
- (void)setFlags:(SCNetworkReachabilityFlags)flags {
    dispatch_barrier_async(_synchronizationQueue, ^{
        self->_flags = flags;
        [self _notifyAllListeners];
    });
}

- (void)_startMonitoringReachabilityWithURL:(NSURL *)url {
    dispatch_barrier_async(_synchronizationQueue, ^{
        self->_networkReachability = SCNetworkReachabilityCreateWithName(NULL, url.host.UTF8String);
        if (self->_networkReachability != NULL) {
            // Set the initial flags
            SCNetworkReachabilityFlags flags;
            SCNetworkReachabilityGetFlags(self->_networkReachability, &flags);
            self.flags = flags;

            // Set up notification for changes in reachability.
            SCNetworkReachabilityContext context = {0, (__bridge void *)(self), NULL, NULL, NULL};
            if (SCNetworkReachabilitySetCallback(self->_networkReachability, _reachabilityCallback, &context)) {
                if (!SCNetworkReachabilitySetDispatchQueue(self->_networkReachability, self->_synchronizationQueue)) {
                    PFLogError(PFLoggingTagCommon, @"Unable to start listening for network connectivity status.");
                }
            }
        }
    });
}

// 同步并发读
- (SCNetworkReachabilityFlags)flags {
    __block SCNetworkReachabilityFlags flags;
    dispatch_sync(_synchronizationQueue, ^{
        flags = self->_flags;
    });
    return flags;
}


总结:并行队列,屏障独写;并发读。 Dispatch_barrier_sync & dispatch_barrier_async 等操作,比较多哦。

BFTask+Private.m

// dispatch_semaphore 等待异步线程执行结果
- (id)waitForResult:(NSError **)error withMainThreadWarning:(BOOL)warningEnabled {
    ...
        dispatch_semaphore_t semaphore = dispatch_semaphore_create(0);
        [self continueWithBlock:^id(BFTask *task) {
            dispatch_semaphore_signal(semaphore);
            return nil;
        }];
        dispatch_semaphore_wait(semaphore, DISPATCH_TIME_FOREVER);
    ...
}

总结:异步等待执行结果, dipsatch_semaphore 可以实现这个效果。dispatch_group 也可以实现相同的效果。

PFURLSession.m

// 并发队列
_delegatesAccessQueue = dispatch_queue_create("com.parse.urlSession.delegates", DISPATCH_QUEUE_CONCURRENT);

// 同步并发读
- (PFURLSessionDataTaskDelegate *)_taskDelegateForTask:(NSURLSessionTask *)task {
    __block PFURLSessionDataTaskDelegate *delegate = nil;
    dispatch_sync(_delegatesAccessQueue, ^{
        delegate = self->_delegatesDictionary[@(task.taskIdentifier)];
    });
    return delegate;
}

// 异步屏障写操作
- (void)setDelegate:(PFURLSessionDataTaskDelegate *)delegate forDataTask:(NSURLSessionDataTask *)task {
    dispatch_barrier_async(_delegatesAccessQueue, ^{
        self->_delegatesDictionary[@(task.taskIdentifier)] = delegate;
    });
}

- (void)_removeDelegateForTaskWithIdentifier:(NSNumber *)identifier {
    dispatch_barrier_async(_delegatesAccessQueue, ^{
        [self->_delegatesDictionary removeObjectForKey:identifier];
    });
}

总结:并发读 ,屏障独写 dispatch_barrier_async & dispatch_barrier_sync, dispatch_sync 同步读。

PFCoreManager.m

总结:多串行队列,每个队列的意义明确,有不同的作用,保证数据安全。

上一篇下一篇

猜你喜欢

热点阅读