2013-08-22 4 views
1

iOS의 목표 C에서 역 지오 코딩을 사용하여 도시를 반환하는 데 문제가 있습니다. completionHandler 내에서 도시를 로그 할 수 있지만 다른 함수에서 호출 된 경우이를 문자열로 반환하는 방법을 알아낼 수 없습니다.역 지오 코드 - 지역 반환

도시 변수는 헤더 파일에서 생성 된 NSString입니다.

- (NSString *)findCityOfLocation:(CLLocation *)location 
{ 

    geocoder = [[CLGeocoder alloc] init]; 
    [geocoder reverseGeocodeLocation:location completionHandler:^(NSArray *placemarks, NSError *error) { 

     if ([placemarks count]) 
     { 

      placemark = [placemarks objectAtIndex:0]; 

      city = placemark.locality; 

     } 
    }]; 

    return city; 

} 

답변

7

디자인이 잘못되었습니다.

비동기 호출을 수행 중이므로 메소드에서 값을 동기식으로 반환 할 수 없습니다.

completionHandler은 향후에 호출 될 블록이므로 블록 호출시 결과를 처리하기 위해 코드 구조를 변경해야합니다. 전과 돌아갑니다 findCityOfLocation 방법을 의미 비동기 (나는 보통 선호)

- (void)findCityOfLocation:(CLLocation *)location { 
    geocoder = [[CLGeocoder alloc] init]; 
    typeof(self) __weak weakSelf = self; // Don't pass strong references of self inside blocks 
    [geocoder reverseGeocodeLocation:location completionHandler:^(NSArray *placemarks, NSError *error) { 
     if (error || placemarks.count == 0) { 
      [weakSelf didFailFindingPlacemarkWithError:error]; 
     } else { 
      placemark = [placemarks objectAtIndex:0]; 
      [weakSelf didFindPlacemark:placemark]; 
     } 
    }]; 
} 

- (void)didFindPlacemark:(CLPlacemark *)placemark { 
    // do stuff here... 
} 

- (void)didFailFindingPlacemarkWithError:(NSError *)error { 
    // handle error here... 
} 

또는 블록

- (void)findCityOfLocation:(CLLocation *)location completionHandler:(void (^)(CLPlacemark * placemark))completionHandler failureHandler:(void (^)(NSError *error))failureHandler { 
    geocoder = [[CLGeocoder alloc] init]; 
    [geocoder reverseGeocodeLocation:location completionHandler:^(NSArray *placemarks, NSError *error) { 
     if (failureHandler && (error || placemarks.count == 0)) { 
      failureHandler(error); 
     } else { 
      placemark = [placemarks objectAtIndex:0]; 
      if(completionHandler) 
       completionHandler(placemark); 
     } 
    }]; 
} 

//usage 
- (void)foo { 
    CLLocation * location = // ... whatever 
    [self findCityOfLocation:location completionHandler:^(CLPlacemark * placemark) { 
     // do stuff here... 
    } failureHandler:^(NSError * error) { 
     // handle error here... 
    }]; 
} 
+0

: 난 당신이 findCityOfLocation 방법에 반환되는 도시에 의존하지 않는 것이 좋습니다,하지만 단지 completionHandler 내에서 도시와 당신이 원하는 작업을 수행 할 것 이 질문에 대한 답변을 – maxmclau

+0

보내 주시면 감사하겠습니다. 답변을 투표 할 수는 없지만 점수 아래의 진드기를 선택하여 수락 할 수 있습니다.) –

+0

죄송합니다. 단 하나의 답을 확인할 수 없었습니다. Fixed – maxmclau

1

역 지오 코딩 요청이 발생 : 당신이 콜백을 사용할 수 있습니다 예를 들어

completionHandler는 응답을 처리합니다. 나는 내가 할 수있는 소원, 덕분에 지금이 볼

- (void)findCityOfLocation:(CLLocation *)location 
{ 

    geocoder = [[CLGeocoder alloc] init]; 
    __weak typeof(self) weakSelf = self; 
    [geocoder reverseGeocodeLocation:location completionHandler:^(NSArray *placemarks, NSError *error) { 

     if ([placemarks count]) 
     { 

      placemark = [placemarks objectAtIndex:0]; 

      weakSelf.city = placemark.locality; 

      // we have the city, no let's do something with it 
      [weakSelf doSomethingWithOurNewCity]; 
     } 
    }];  
}