2010-02-18 4 views
3

J'essaie de filtrer un tableau d'objets qui forment essentiellement un graphe arborescent. ce que je veux faire est de filtrer tous les objets de ce tableau dont la propriété visible est NO, ou si sa propriété visible parent/grandparent/etc est vraie (les objets enfants peuvent avoir la propriété visible YES alors que son parent peut être NO). Je ne comprends pas comment j'utiliserais la syntaxe NSPredicate pour continuer à chercher le nœud parent jusqu'à ce qu'il n'y ait plus de parents ou que la propriété visible soit trouvée. Y a-t-il un moyen de s'y prendre?Un NSPredicate qui peut parcourir récursivement un graphe d'objet?

Répondre

1

Son depuis un certain temps j'ai posé cette question, et je pense que je suis allé dans une autre direction avec ce que je faisais, mais il y a des possibilités que je me rends compte maintenant pour résoudre ce que je voulais à l'époque:

  • Avoir la méthode de propriété visible se comporter récursivement au lieu de faire le prédicat de format faire cela. Cela pourrait se faire comme ceci:
- (BOOL) isVisible { 
    return visible && [parent isVisible]; 
} 

//... 
id filtered = [array filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"visible == YES"]]; 
  • Utiliser le bloc prédicats au lieu du format prédicats pour faire le traversal récursive:
[array filteredArrayUsingPredicate:[NSPredicate predicateWithBlock:^BOOL(id evaluatedObject, NSDictionary *bindings) { 

    id obj = evaluatedObject; 
    while (obj) { 
     if (![obj isVisible]) return NO; 
     obj = [obj parent]; 
    } 
    return YES; 
}]]; 

Ou une combinaison de les deux (ce qui serait le plus robuste et lisible je pense).

0

Je ne suis pas sûr que ce que vous cherchez à faire est possible avec un seul prédicat simple. Si c'est un arbre et que vous utilisez un prédicat pour obtenir les noeuds, vous voudrez et écrivez une méthode qui ira vers le haut et retournera un BOOL indiquant s'il doit être supprimé ou non.

Puis, juste obtenir vos nœuds et les mettre dans un NSMutableArray et faire un

for (int i = 0; i < [results count]; i++) 
{ 
    if ([self shouldBeRemoved:[results objectAtIndex:i]]) 
    { 
     [results removeObjectAtIndex:i]; 
     i--; 
    } 
} 

Votre shouldBeRemoved: méthode devrait être assez une méthode récursive simple.

Questions connexes