2016-04-02 6 views
2

Ich versuche, einen K-nn-Klassifikator zu implementieren. Ein Teil dieses Problems besteht darin, den euklidischen Abstand von einem Beispiel zu einem anderen zu erhalten. Ich habe Probleme, es zu berechnen, weil sum schließlich NaN ist.NaN in C++ warum?

Das Problem ist in diesem Codeblock:

for(int i=0;i<fdataset.size();i++){ 
    float sum=0; 
    for(int k=0;k<fdataset[i].size();k++){ 
    if(mask[k]){ 
     sum+=(fdataset[i][k]-example[k])*(fdataset[i][k]-example[k]); 
    } 
    } 
    results[i]=sqrt(sum); 
} 

fdataset ist ein vector< vector<float> > und examplevector<float> ist. Es sollte keine Probleme geben. Also, warum habe ich dieses Problem?

Danke!

+1

"Wenn das Argument kleiner als -0 ist, wird FE_INVALID ausgelöst und NaN wird zurückgegeben." aus ['std :: sqrt'] (http://en.cppreference.com/w/cpp/numeric/math/sqrt) – Maikel

+3

@Maikel wann kann' sum' negativ sein? '(fdataset [i] [k] -Beispiel [k]) * (fdataset [i] [k] -Beispiel [k])' ist immer positiv oder "0" – YnkDK

+0

Ist Summe NaN oder enthalten die Ergebnisse NaN? – stefaanv

Antwort

2

Die wahrscheinlichste Erklärung ist, dass Ihr Datensatz mit einem oder mehreren NaN "vergiftet" ist. Es würde nur ein einzelnes NaN in den fdataset oder example Arrays benötigen, um sum zu korrumpieren.

Als Hilfe beim Debugging können Sie jeden Eingang mit std::isnan() überprüfen.

Update: Wie Benutzer akavel in einem Kommentar vorgeschlagen, gibt es andere Ausdrücke, die auch NaN in IEEE 754 Fließkommaarithmetik generieren können. Wikipedia lists them here. Ich glaube, dass die relevanten Operationen Code sind:

  • Vorgänge, bei denen einer der Operanden ein NaN
  • 0 * inf
  • inf - inf

So sollten Sie auch prüfen, ob Ihre Eingaben sind nicht inf mit std::isinf().

+0

Auch wenn einige Werte Überlauf schweben sie könnte anscheinend [werden INF] (http://www.cquestions.com/2011/02/float-overflow-in-c.html), und INF-INF ist NaN ich denke – akavel

+0

Danke für deine Antwort, Ross. Wie Sie sagen, mein Datensatz wurde mit -nan-Werten vergiftet, also habe ich den Mindestwert des Bereichs vergifteten Werten zugewiesen. Jetzt funktioniert mein Klassifikator besser als vorher. Unerklärlicherweise arbeitete mein Klassifikator mit nan-Werten. – Carlos