2010-01-08 7 views
14

Mein verwaltetes Objekt hat 2 doppelte Felder: "latitude", "longitude". Ich brauche alle Objekte zu holen, dieNSPredicate funktioniert nicht mit doppelten Werten (% f)?

bestimmte Koordinaten hat

Dieser Code funktioniert nicht, fetchedObjects count = 0

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"latitude == %f AND longitude == %f", coordinate.latitude, coordinate.longitude]; 

Aber dieser Code funktionieren, zählen fetchedObjects = 3:

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"latitude == 53.012667 AND longitude == 36.113000"]; 

Antwort

25

es funktioniert gut mit langem Schwimmer,% lf

+0

Akzeptieren Sie Ihre Antwort als richtig, wenn es Ihr Problem löst – Vladimir

+3

Wie jdeprez angegeben Sie sollten nicht Float-Werte werden verglichen. Das Vergleichen von Float-Werten ist gefährlich und eine schlechte Übung. Verwenden Sie stattdessen eine große Region als Prädikat, und berechnen Sie dann die Entfernung von dem Punkt, der der gesuchten Position am nächsten ist, aus dem Array der zurückgegebenen Objekte. – Christopher

+0

Sie haben meinen Tag gerettet ..... :-) –

14

Oh geez ...

Verwenden Sie niemals ==, um Gleitkommawerte zu vergleichen.

Wenn Sie Objekte mit einem "spezifischen" Wert suchen möchten, vergleichen Sie sie mit einem kleinen Bereich. Andernfalls wird ein Gleitkommadarstellungsfehler Sie beißen.

So prüfen, mit:

const float epsilon = 0.000001; 
NSPredicate *predicate = [NSPredicate predicateWithFormat:@"latitude > %f AND latitude < %f AND longitude > %f AND longitude < %f", coordinate.latitude - epsilon, coordinate.latitude + epsilon, coordinate.longitude - epsilon, coordinate.longitude + epsilon]; 
+1

Clang's ** float.h ** definiert eine Anzahl von Konstanten, die für Floats und Doubles relevant sind. Zwei davon sind "FLT_EPSILON" (1E-5) und "DBL_EPSILON" (1E-9), die anstelle des hier angegebenen Epsilons 1E-6 verwendet werden sollten. Eigenschaften dieser Konstanten sind definiert durch [C99 5.2.4.2.2] (http://c0x.coding-guidelines.com/5.2.4.2.2.html). –

+1

Verwenden Sie '% lf', wenn Sie gegen Doubles – ken

2

Es ist, weil die Präzision der Schwimmer nicht zu 100% ist. So können Sie auch dies tun:

[NSPredicate predicateWithFormat:@"abs(latitude - %f) < 0.0001 AND abs(longitude - %f) < 0.0001", coordinate.latitude, coordinate.longitude] 
+0

vergleichen Ich bekomme diese Fehlermeldung:' '' 'Ungültiges Prädikat', Grund: 'Die Funktion' abs: 'wird nicht unterstützt.''' –

0

Konvertieren in NSNumber dies mit:

NSPredicate *predicate = [NSPredicate predicateWithFormat:@"latitude == %@ AND longitude == %@", @(coordinate.latitude), @(coordinate.longitude)]; 
Verwandte Themen