2012-01-16 54 views
2

是否可以爲局部變量賦值一個值,該值的範圍在塊之外並保留其值?特別是,我爲iOS編碼,並且我在另一個塊中有一個嵌套塊,我想爲該塊內的值分配一個NSString值,稍後(在塊外)使用它。我嘗試使用__block螺母時,我指的是NSString塊後,我得到一個錯誤的訪問錯誤。我使用ARC是重要的。例如:Obj-C:__block變量

__block NSString *str; 

someBlock ^(id param1) 
{ 
    str = @"iPhone"; 
} 

[str getCharAtIndex:1]; //or w/e 

我在做什麼概念上錯誤或這不允許或什麼?非常感謝幫助。

編輯:

這裏的實際代碼,基本代碼獲取的鳴叫作爲JSON對象,然後所有我特林做的是顯示文本。在代碼中我沒有提取從JSON文本,我試圖做一個概念證明

- (IBAction)getTweet:(id)sender 
{ 
    __block NSString *displayStr; 

    //account instance 
    ACAccountStore *store = [[ACAccountStore alloc] init]; 
    ACAccountType *twitterAcountType = 
       [store accountTypeWithAccountTypeIdentifier: ACAccountTypeIdentifierTwitter]; 

    //request access 
    [store requestAccessToAccountsWithType: twitterAcountType withCompletionHandler: 
    ^(BOOL granted, NSError *error) 
    { 
     if (!granted) { 
      //display error on textView 
     } 
     else 
     { 
      //get available accounts 
      NSArray *twitterAccounts = [store accountsWithAccountType: twitterAcountType]; 

      if([twitterAccounts count] > 0) 
      { 
       //get first account 
       ACAccount *account = [twitterAccounts objectAtIndex: 0]; 

       ////make authenticated request to twitter 
       //set-up params 
       NSMutableDictionary *params = [[NSMutableDictionary alloc] init]; 
       [params setObject:@"1" forKey:@"include_entities"]; 
       [params setObject:@"1" forKey:@"count"]; 

       //which REST thing to call 
       NSURL *url = 
       [NSURL URLWithString:@"http://api.twitter.com/1/statuses/home_timeline.json"]; 

       //create request 
       TWRequest *request = 
       [[TWRequest alloc] 
         initWithURL:url parameters:params requestMethod:TWRequestMethodGET]; 

       //attach account info 
       [request setAccount: account]; 
       [request performRequestWithHandler: 
        ^(NSData *responseData, NSHTTPURLResponse *urlResponse, NSError *error) 
        { 
        if(error != nil) 
        { 
         //display error 
        } 
        else 
        { 
         NSError *jsonError; 
         NSArray *timeline = 
          [NSJSONSerialization 
            JSONObjectWithData: responseData 
            options: NSJSONReadingMutableLeaves 
            error: &jsonError]; 

         if (jsonError == nil) 
         { 
          /////////////////////////// 
          ///heres the src of error// 
          /////////////////////////// 
          //display data 
          NSLog(@"array: %@", timeline); 
          displayStr = @"whats the deal with this"; 

     //i tried this but i think ARC takes care of this 
          [displayStr retain]; 
         } 
         else 
         { 
          //display error 
         } 
        } 

        }];//end block de request 
      } 
      else 
      { 
       //display error 
      } 
     } 
    }];//end block de store 

    ///////then heres where i get the bad access error 
    [self.lastTweetText setText:displayStr]; 


}//end getTweet 

也感謝幫助傢伙

回答

1

首先,str只有在塊被執行後纔會更新。所以除非你使用dispatch_sync作爲該塊,否則在這一行:[str getCharAtIndex:1];該塊不太可能被執行,而str也不會被更新。

其次,如果您不使用ARC,則__block變量不會自動保留在塊對象中。這意味着如果你沒有保留它,比你訪問str時,str可能是一個解除分配的對象並導致你的應用程序崩潰。

3

你只是定義該塊,但不執行它。致電someBlock(valueForParam1);執行您的區塊。否則你的str指針指向一些垃圾,並調用getCharAtIndex:崩潰你的應用程序。

+0

'str'實際上不會指向垃圾,它會指向零,因爲ARC零對象指針。 – hypercrypt 2012-01-16 14:39:07

+0

你是對的。我忽略了它啓用了ARC的事實。 – V1ru8 2012-01-16 15:48:37

1

你只是簡單地定義你的區塊,但不能調用它。

嘗試此:)

__block NSString *str; 
void (^someBlock)(id) = ^(id param1) 
{ 
    str = @"iPhone"; 
}; 
someBlock(nil); 
[str getCharAtIndex:1]; 

在這種情況下我直接調用它,但通常塊本身是一些方法或函數的參數。