2013-03-21 11 views
9

Quando si stampa la descrizione di un NSThread, si ottiene qualcosa di simile:NSThread number su iOS?

<NSThread: 0x1e511b70>{name = (null), num = 1} 

È questo il "numero" a disposizione in qualche modo?

Questo è solo per il debug, quindi non è necessario cancellare il processo di approvazione di Apple.

+0

Forse è in '- [ threadDictionary]'? (È possibile memorizzare le informazioni locali del thread in "NSThread''s _threadDictionary _...) – nielsbot

+0

Ottima idea, ma nessun dado: è vuoto. :) –

+0

Non è solo il suo puntatore? Potrebbe non essere uguale all'ID del thread stampato da NSLog. –

risposta

11

Quel numero è in realtà un Ivar nella classe di implementazione privata di NSThread. La classe è _NSThreadInternal, e il suo nome è All'interno di questo oggetto, l'ivar è seqNum

È possibile estrarlo direttamente se si è disposti a fare affidamento su percorsi chiave non documentati. Questo lo farà (e buona chiamata neilsbot sull'utilizzo di valueForKeyPath invece di runtime chiamate):

@implementation NSThread (GetSequenceNumber) 

- (NSInteger)sequenceNumber 
{ 
    return [[self valueForKeyPath:@"private.seqNum"] integerValue]; 
} 

@end 

L'ho provato impostando manualmente ivar con le chiamate di runtime e poi NSLoggiando il thread. Abbastanza sicuro, la descrizione riflette il cambiamento. Questo ovviamente non è documentato, quindi ...

... utilizzare a proprio rischio.

È un esercizio divertente, ma le cose sono in genere private per un motivo. Il codice spedito dovrebbe certamente evitare cose del genere a meno che tutte le altre rotte non siano state completamente esaurite.

+0

Lo sto testando ora, ma sembra perfetto. –

+1

Sì, questo è perfetto. Nota che questo deve essere fatto nel file che non usa ARC. Ma dal momento che puoi combinare e abbinare ARC e non, non è un problema. –

+0

Buon punto Stephen, l'ho frustato in un vecchio progetto che era aperto. L'ho aggiornato per essere ARC-friendly (e più bello in generale). –

6

sono andato avanti e ho scritto il suggerimento di @ XLC, solo perché:

@implementation NSThread (ThreadGetIndex) 

-(NSInteger)getThreadNum 
{ 
    NSString * description = [ self description ] ; 
    NSArray * keyValuePairs = [ description componentsSeparatedByString:@"," ] ; 
    for(NSString * keyValuePair in keyValuePairs) 
    { 
     NSArray * components = [ keyValuePair componentsSeparatedByString:@"=" ] ; 
     NSString * key = components[0] ; 
     key = [ key stringByTrimmingCharactersInSet:[ NSCharacterSet whitespaceCharacterSet ] ] ; 
     if ([ key isEqualToString:@"num" ]) 
     { 
      return [ components[1] integerValue ] ; 
     } 
    } 
    @throw @"couldn't get thread num"; 
    return -1 ; 
} 

@end 

Ciò risponde alla domanda di ottenere "num" dal filo - anche se la questione legata come una vittima potrebbe essere utile per la domanda generale di identificare in modo univoco i thread.

(La risposta che mi piace c'è "generare un UUID e mettere in nel dizionario filo del filo.)

+0

In questo caso mi piace di più, poiché il numero di thread è più leggibile di un UUID e corrisponde al debugger. Grazie. –

+0

se si sta facendo molto, è possibile modificare questo codice per memorizzare nella cache la ricerca usando 'objc_setAssociatedObject()'/'objc_getAssociatedObject()' – nielsbot