iOS 멀티스레드 개발의 NSOperation 사용법 요약

6790 단어
NSOperation 의 역할
NSOperation 및 NSOperationQueue와 함께 멀티스레드 프로그래밍 가능
NSOperation 및 NSOperationQueue의 멀티스레드 구현 단계
  • 먼저 수행해야 할 작업을 NSOperation 객체에 캡슐화
  • NSOperation 객체를 NSOperationQueue에 추가
  • NSOperationQueue의 NSOperation을 자동으로 제거
  • 제거된 NSOperation 캡슐화된 작업을 새 스레드에 배치
  • 참고:
  • NSOperation은 추상적인 클래스로 봉인 조작 능력을 갖추지 못하므로 반드시 하위 클래스
  • 를 사용해야 한다.
  • NSOperation 하위 클래스를 사용하는 3가지 방법은 다음과 같습니다.
  • NSInvocationOperation
  • NSBlockOperation
  • 자정의 자류가 NSOperation을 계승하여 내부에 상응하는 방법을 실현한다
  • NSInvocation Operation 클래스
  • NSInvocation Operation 객체 작성
  • -(id)initWithTarget:(id)targetselector:(SEL)selobject:(id)arg;
    
  • start 방법을 호출하여 작업을 시작합니다
  • -(void)start;
    

    일단 조작을 실행하면 target의sel 방법을 호출합니다
  • 코드:
  • NSInvocationOperation *op = [[NSInvocationOperation alloc] initWithTarget:self selector:@selector(run) object:nil];
        [op start];
     - (void)run
    {
        NSLog(@"------%@", [NSThread currentThread]);
    }
    
  • 참고:
  • 기본적으로 start 방법을 호출한 후 새로운 라인을 열어 작업을 수행하지 않고 현재 라인에서 동기화
  • NSOperation을 하나의 NSOperationQueue에 배치해야만 비동기적으로 작업을 수행할 수 있음
  • 이런 것들은 이해하기만 하면 개발에서 자주 사용되지 않는다
  • NSBlockOperation 클래스
  • NSBlockOperation 객체 만들기
  • +(id)blockOperationWithBlock:(void(^)(void))block;
    
  • addExecutionBlock: 방법을 통해 더 많은 조작을 추가
  • -(void)addExecutionBlock:(void(^)(void))block;
    
  • 코드:
  •  NSBlockOperation *op = [NSBlockOperation blockOperationWithBlock:^{
            //     
            NSLog(@"  1------%@", [NSThread currentThread]);
        }];
        
        //        (      )
        [op addExecutionBlock:^{
            NSLog(@"  2------%@", [NSThread currentThread]);
        }];
        [op addExecutionBlock:^{
            NSLog(@"  3------%@", [NSThread currentThread]);
        }];
        [op addExecutionBlock:^{
            NSLog(@"  4------%@", [NSThread currentThread]);
        }];
        
        [op start];
    
  • 참고: NSBlockOperation의 캡슐화된 작업 수가 >1이면 비동기적으로 실행
  • NSOperationQueue
  • NSOperationQueue의 역할
  • NSOperation은 start 방법을 호출하여 작업을 수행할 수 있지만 기본적으로 동기화
  • NSOperation을 NSOperationQueue(작업 대기열)에 추가하면 NSOperation의 작업이 자동으로 비동기적으로 수행됩니다
  • .
  • NSOperationQueue에 작업 추가
  • -(void)addOperation:(NSOperation*)op;
    -(void)addOperationWithBlock:(void(^)(void))block;
    
  • 코드:
  • 방법1:
  •     //     
        NSOperationQueue *queue = [[NSOperationQueue alloc] init];
        
        //     
            NSBlockOperation *op1 = [NSBlockOperation blockOperationWithBlock:^{
                NSLog(@"download1 --- %@", [NSThread currentThread]);
            }];
        
        //        
            [queue addOperation:op1];
    
  • 방법2:
  •  //     
        NSOperationQueue *queue = [[NSOperationQueue alloc] init];
    //        
     [queue addOperationWithBlock:^{
            NSLog(@"download1 --- %@", [NSThread currentThread]);
        }];
    

    NSOperationQueue의 대기열 유형과 GCD의 대기열 유형 비교
  • GCD 큐
  • 동시 큐
  • 자체 제작
  • 글로벌
  • 직렬 큐
  • 홈팀 열
  • 자체 제작
  • NSOperationQueue의 큐
  • 홈팀 열
  •     [NSOperationQueue mainQueue]
    
     -             (NSOperation),          
    
  • 비홈팀 열(기타 대기열)
  •      [[NSOperationQueue alloc] init]
    
     -      :  、    
     -            (NSOperation),            
    

    최대 동시 발생
  • 병발수가 무엇인지
  • 동시 작업 수
  • 예를 들어 3개의 라인을 동시에 열어 3개의 임무를 수행하면 병발수는 3
  • 이다.
  • 최대 병발수에 대한 방법
  • -(NSInteger)maxConcurrentOperationCount;
    -(void)setMaxConcurrentOperationCount:(NSInteger)cnt;
    
  • 코드
     //     
     NSOperationQueue *queue = [[NSOperationQueue alloc] init]; 
     //          
     // queue.maxConcurrentOperationCount = 2;//     
     queue.maxConcurrentOperationCount = 1; //         
     //     
     [queue addOperationWithBlock:^{
          NSLog(@"download1 --- %@", [NSThread currentThread])
      }];
     [queue addOperationWithBlock:^{
          NSLog(@"download2 --- %@", [NSThread currentThread])
      }];
     [queue addOperationWithBlock:^{
          NSLog(@"download3 --- %@", [NSThread currentThread])
      }];
    
    
  • 대기열의 취소, 일시 중지, 복원
  • 큐의 모든 작업 취소
  • -(void)cancelAllOperations;
    

    팁: NSOperation의 - (void) cancel 메서드를 호출하여 개별 작업을 취소할 수도 있습니다.
  • 일시 중지 및 복구 대기열
  •   -(void)setSuspended:(BOOL)b;// YES      ,NO      
      - (BOOL)isSuspended
    
  • 코드
  •  //     ,    
     // self.queue.suspended = NO;
    
     //   (  )  ,    
     // self.queue.suspended = YES;
    
     //          
     [self.queue cancelAllOperations];
    

    운영 의존성
  • NSOperation 간 의존성을 설정하여 실행 순서를 보장할 수 있음
  • 예를 들어 반드시 조작 A를 실행한 후에야 조작 B를 실행할 수 있다
  • [operationB addDependency:operationA];//   B     A
    
  • queue가 다른 NSOperation 간에 의존 관계를 만들 수 있음
  • 코드
  •     //     
        NSOperationQueue *queue = [[NSOperationQueue alloc] init];
        //     
        NSBlockOperation *op1 = [NSBlockOperation blockOperationWithBlock:^{
            NSLog(@"download1----%@", [NSThread  currentThread]);
        }];
        NSBlockOperation *op2 = [NSBlockOperation blockOperationWithBlock:^{
            NSLog(@"download2----%@", [NSThread  currentThread]);
        }];
        NSBlockOperation *op3 = [NSBlockOperation blockOperationWithBlock:^{
            NSLog(@"download3----%@", [NSThread  currentThread]);
        }];
       //     (  op3 op1 op2         )
        [op3 addDependency:op1];
        [op3 addDependency:op2];
    
  • 주의: 서로 의존할 수 없음
  • 예를 들어 A는 B에 의존하고 B는 A에 의존한다
  • 스레드 간 통신
  • 예: 하위 라인에서 그림을 다운로드하고 주 라인에 대답하고 이미지 뷰에 그림 추가
  • 코드 보기:
  •    [[[NSOperationQueue alloc] init] addOperationWithBlock:^{
            //        
            NSURL *url = [NSURL URLWithString:@"http://img.pconline.com.cn/images/photoblog/9/9/8/1/9981681/200910/11/1255259355826.jpg"];
            
            //     
            NSData *data = [NSData dataWithContentsOfURL:url];
            
            //     
            UIImage *image = [UIImage imageWithData:data];
            
            //      
            [[NSOperationQueue mainQueue] addOperationWithBlock:^{
                self.imageView.image = image;
            }];
        }];
    

    조작의 감청
  • 한 조작의 실행 완료를 감청할 수 있음
  • -(void(^)(void))completionBlock;
    -(void)setCompletionBlock:(void(^)(void))block;
    

    NSOperation 사용자 지정
  • NSOperation 사용자 정의 절차는 간단합니다
  • 다시 쓰기-(void)main 방법으로 실행하고 싶은 임무를 수행
  • 다시 쓰기-(void)main 방법의 주의점
  • 스스로 자동 방출 탱크를 생성한다
  • 자주 - (BOOL) isCancelled 방법을 통해 작업이 취소되었는지 확인하고 취소에 응답
  • 좋은 웹페이지 즐겨찾기