Domanda

Ho una serie di dizionari.

Voglio filtrare l'array in base a una chiave.

Ho provato questo:

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"(SPORT ==  %@)", @"Football"];

NSArray *filteredArray = [data filteredArrayUsingPredicate:predicate];

Questo non funziona, ottengo alcun risultato. Penso che sto facendo qualcosa di sbagliato. So che questo è il metodo se "SPORT" è stato un Ivar. Penso che probabilmente è diverso se si tratta di una chiave.

Non sono stato in grado di trovare un esempio però.

Grazie


Aggiorna

ho aggiunto le virgolette attorno alla stringa che sto cercando.

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"(SPORT ==  '%@')", @"Football"];

E 'ancora non funziona.


Aggiorna 2

Risolto esso. Ho dovuto togliere le virgolette singole, che sembra andare contro quello che dice la guida.

Il mio vero problema è che ho avuto un array nidificato e non ero in realtà la valutazione dei dizionari. osso testa di movimento.

È stato utile?

Soluzione

Dovrebbe funzionare - fino a quando la variabile di dati è in realtà un array che contiene un dizionario con la chiave SPORT

NSArray *data = [NSArray arrayWithObject:[NSMutableDictionary dictionaryWithObject:@"foo" forKey:@"BAR"]];    
NSArray *filtered = [data filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"(BAR == %@)", @"foo"]];

filtrata in questo caso contiene il dizionario.

(l'% @ non deve essere citato, questo viene fatto quando NSPredicate crea l'oggetto.)

Altri suggerimenti

Lo so che è una notizia vecchia, ma di aggiungere i miei due centesimi. Per impostazione predefinita, io uso i comandi LIKE[cd] piuttosto che solo [c]. Il [d] confronta lettere con simboli di accento. Questo funziona bene soprattutto nel mio Warcraft App in cui la gente incantesimo il loro nome "voodoo" rendendo quasi impossibile per cercare il loro nome in un Tableview. Il [d] strisce loro simboli accento durante il predicato. Quindi, un predicato di @"name LIKE[CD] %@", object.name dove object.name == @"voodoo" restituirà l'oggetto che contiene il nome del voodoo.

Dalla documentazione di Apple: come [cd] significa “maiuscole e diacritic-insensibile come”). Per una descrizione completa della sintassi di stringa e un elenco di tutti gli operatori disponibili, vedere Predicate Format String Sintassi .

#import <Foundation/Foundation.h>
// clang -framework Foundation Siegfried.m 
    int
main() {
    NSArray *arr = @[
        @{@"1" : @"Fafner"},
        @{@"1" : @"Fasolt"}
    ];
    NSPredicate *p = [NSPredicate predicateWithFormat:
        @"SELF['1'] CONTAINS 'e'"];
    NSArray *res = [arr filteredArrayUsingPredicate:p];
    NSLog(@"Siegfried %@", res);
    return 0;
}

NSPredicate è disponibile solo in iPhone 3.0.

Non si dovrebbe notare che fino a cercare di eseguire sul dispositivo.

Con Swift 3, quando si desidera filtrare una serie di dizionari con un predicato in base a chiavi e valori del dizionario, è possibile scegliere uno dei seguenti modelli.


# 1. Utilizzando NSPredicate init(format:arguments:) inizializzazione

Se si proviene da Objective-C, init(format:arguments:) offre uno stile di codifica di valori-chiave per valutare la vostra predicato.

Utilizzo:

import Foundation

let array = [["key1": "value1", "key2": "value2"], ["key1": "value3"], ["key3": "value4"]]

let predicate = NSPredicate(format: "key1 == %@", "value1")
//let predicate = NSPredicate(format: "self['key1'] == %@", "value1") // also works
let filteredArray = array.filter(predicate.evaluate)

print(filteredArray) // prints: [["key2": "value2", "key1": "value1"]]

# 2. Utilizzando NSPredicate init(block:) inizializzazione

In alternativa, se si preferisce fortemente tipizzato API oltre / API stringly digitati, è possibile utilizzare init(block:) inizializzatore.

Utilizzo:

import Foundation

let array = [["key1": "value1", "key2": "value2"], ["key1": "value3"], ["key3": "value4"]]

let dictPredicate = NSPredicate(block: { (obj, _) in
    guard let dict = obj as? [String: String], let value = dict["key1"] else { return false }
    return value == "value1"
})

let filteredArray = array.filter(dictPredicate.evaluate)
print(filteredArray) // prints: [["key2": "value2", "key1": "value1"]]

Guardando il NSPredicate riferimento , sembra che tu abbia bisogno di circondare il vostro personaggio sostituzione con le citazioni. Ad esempio, il predicato corrente si legge: (SPORT == Football) lo si vuole leggere (SPORT == 'Football'), così il vostro stringa di formato deve essere @"(SPORT == '%@')"

.
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top