Como você testa para ver se um dobro é igual a NaN?

283

Eu tenho um duplo em Java e quero verificar se é NaN. Qual é a melhor maneira de fazer isso?

Eric Wilson
fonte

Respostas:

475

Use a estática Double.isNaN(double)método, ou o seu Double's .isNaN()método.

// 1. static method
if (Double.isNaN(doubleValue)) {
    ...
}
// 2. object's method
if (doubleObject.isNaN()) {
    ...
}

Simplesmente fazendo:

if (var == Double.NaN) {
    ...
}

não é suficiente devido à definição do padrão IEEE para NaN e números de ponto flutuante .

Ben S
fonte
51
Outra maneira de fazer isso seria v! = V. Somente NaN compara false consigo mesmo. Mas não faça isso, isNaN é um milhão de vezes melhor. :)
Joren
5
@Joren, antes tarde do que nunca: 'isNaN' é realmente melhor usar do que v! = V para facilitar a leitura. Mas o código-fonte do método isNaN é exatamente o mesmo que dizer v! = V. Fonte: public boolean estático isNaN (double v) {return (v! = V); }
Rolf #
1
Double.isNaN should be (true) resposta agradável
Oliver Shaw
@Joren isNaN basta verificar v = v;) mas parece melhor!
Sr. Jedi
O uso do Java 5: value == Double.NaNnão funciona, mas Double.isNaN(value)funciona bem.
Zero01alpha 6/12/16
45

Tente Double.isNaN():

Retorna true se esse valor Double for um NaN (Not-a-Number), caso contrário, false.

Observe que [ double.isNaN()] não funcionará, porque as duplas sem caixa não têm métodos associados a elas.

Andrew Hare
fonte
Eu pensei que você não poderia chamar métodos em tipos primitivos em Java. Realmente precisa ser Double.isNan()e não double.IsNan(), certo?
Joren
Joren, ele está confiando no autobox (o dobro é convertido em Double pelo compilador / tempo de execução); novo recurso a partir de 1.5. Pouco risco de ir nessa direção; Passar de Duplo para Duplo cria risco de NullPointerExceptions.
M1EK 21/09/09
Eu pensei que a autoboxing funcionasse apenas usando o double como argumento, adicionando-o a uma coleção e coisas do gênero. Tente declarar x duplo e depois pedir x para isNaN () - me dá um erro do compilador.
Carl
Realmente, suspeito que Andrew tenha perdido a tecla Shift digitando o primeiro "duplo".
Carl
14

Convém verificar também se um valor é finito via Double.isFinite(value). Desde o Java 8, existe um novo método na Doubleclasse em que você pode verificar imediatamente se um valor não é NaN e infinito.

/**
 * Returns {@code true} if the argument is a finite floating-point
 * value; returns {@code false} otherwise (for NaN and infinity
 * arguments).
 *
 * @param d the {@code double} value to be tested
 * @return {@code true} if the argument is a finite
 * floating-point value, {@code false} otherwise.
 * @since 1.8
 */
public static boolean isFinite(double d)
Grzegorz Gajos
fonte
10

Você pode verificar o NaN usando var != var. NaNnão é igual NaN.

EDIT : Este é provavelmente o pior método. É confuso, terrível para facilitar a leitura e as más práticas gerais.

HyperNeutrino
fonte
3
Alguém pode explicar o voto negativo? Eu sei, esse caminho é muito ruim e isNané melhor para facilitar a leitura, mas funciona, certo? E o isNanmétodo usa isso para verificar NaN.
HyperNeutrino 12/10
1
Acho que o voto negativo foi porque dessa maneira é muito ruim e isNaN é melhor para facilitar a leitura.
Edward Falk
1
Não diminuí a votação, mas acho que comentários adicionais seriam úteis aqui: se você comparar wrappers como Float ou Double, você acaba comparando referências dessa maneira, não os valores delas, o que definitivamente não é o que você deseja.
Battle_Slug
3
@Battle_Slug Obrigado pelo comentário. Sei que essa é uma péssima idéia, mas coloquei aqui por completo.
HyperNeutrino
isNaNfaz isso sob o capô, mas como funciona? Como algo não se iguala ??
wilmol 08/07/19
0

Iniciantes precisa de exemplos práticos. então tente o seguinte código.

public class Not_a_Number {

public static void main(String[] args) {
    // TODO Auto-generated method stub

    String message = "0.0/0.0 is NaN.\nsimilarly Math.sqrt(-1) is NaN.";        
    String dottedLine = "------------------------------------------------";     

    Double numerator = -2.0;
    Double denominator = -2.0;      
    while (denominator <= 1) {
        Double x = numerator/denominator;           
        Double y = new Double (x);
        boolean z = y.isNaN();
        System.out.println("y =  " + y);
        System.out.println("z =  " + z);
        if (z == true){
            System.out.println(message);                
        }
        else {
            System.out.println("Hi, everyone"); 
        }
        numerator = numerator + 1;
        denominator = denominator +1;
        System.out.println(dottedLine);         
    } // end of while

} // end of main

} // end of class
pggajendra babu
fonte
2
Este exemplo faz muito, e não está claro o que você estava tentando mostrar. Este é apenas um monte de código fragmentado.
Jared Hooper
3
Como o OP, que era iniciante quando essa pergunta foi feita em 09, posso garantir que a resposta aceita foi muito mais útil do que esse exemplo "prático" teria sido.
Eric Wilson
Obrigado @pggajendra babu por postar este código de exemplo.
datnt 26/03
0

O trecho de código abaixo ajudará a avaliar o tipo primitivo que contém NaN.

double dbl = Double.NaN; Double.valueOf(dbl).isNaN() ? true : false;

Teela
fonte