În Java, „NaN” înseamnă „Not a Number”. Nu este un tip de excepție, mai degrabă surprinzător, tipul de date al NaN este, de asemenea, un număr. Dar adesea, când programatorii începători îl obțin neintenționat, îl folosesc în continuare în calculele lor. Prin urmare, tipurile de date incompatibile în Java atunci când sunt utilizate împreună pot provoca o eroare care poate fi aruncată. De asemenea, se vede în mod obișnuit că
De exemplu, aruncați o privire la următorul fragment.
java.lang.ArithmeticException: / by zero
este considerat la fel cu NaN. Cu toate acestea, Java le tratează pe ambele în mod diferit. Destul de derutant? Pentru înțelegerea dvs. cuprinzătoare, vom analiza modul în care acestea sunt diferite unele de altele. Până la sfârșitul acestui articol, veți afla despre posibilele operațiuni care nu produc un număr (nan) și câteva modalități ușoare de a-l gestiona.
Ce este NaN?
Deci, ce este NaN? „NaN”, după cum mulți dintre voi ați ghicit, este folosit pentru a reprezenta „Nu este un număr” în Java. Este o valoare specială în virgulă mobilă pentru a indica depășiri și erori. Este generat atunci când un număr în virgulă mobilă este împărțit la zero sau dacă se calculează rădăcina pătrată a unui număr negativ.
public class NaN
{
public static void main(String[]args)
{
System.out.println(0.0 / 0.0); //zero divided by zero
System.out.println(Math.sqrt(-1)); //take sqrt of negative number
System.out.println(10.0 % 0); //taking mod by zero
}
}
Ieșire
NaN
NaN
NaN
În fragmentul de mai sus, puteți observa că NaN este produs ca urmare a 3 operații simple:
- Împărțirea unui
float / double
zero cu zero. - Luarea sub rădăcină a unui număr negativ (Math.sqrt(-x)). În matematică, luarea rădăcinii pătrate a unui număr negativ are ca rezultat un număr imaginar . Acest caz este tratat prin returnarea NaN în Java.
- Luând modificarea unui număr cu zero, va returna restul după împărțirea unei valori la zero. Prin urmare, NaN este returnat.
Cum este NaN diferit de infinitul pozitiv și negativ?
Conform specificației IEEE 754, există trei valori speciale în virgulă mobilă și duble pentru a gestiona cazurile limită:- Infinitul pozitiv
- Infinitul negativ
- NaN
Ce este metoda NaN()?
isNaN()
este una dintre metodele de bază din Java pentru a verifica dacă este o valoare NaN sau nu. După cum am discutat trei cazuri mai sus, este timpul să testăm modul în care metoda isNaN() diferențiază între valorile +infinity , -infinity și NaN.
public class isNaN
{ public static void main(String[]args)
{
Double posInfinity = +2.0 / 0.0;
Double negInfinity = -3.5 / 0.0;
Double nanVal = 50 % 0.0;
System.out.println ("+" + posInfinity + ".IsNaN() = " + posInfinity.isNaN());
System.out.println ( negInfinity + ".IsNaN() = " + negInfinity.isNaN());
System.out.println ( nanVal + ".IsNaN() = " + nanVal.isNaN());
}
}
Ieșire
+Infinity.IsNaN() = false
-Infinity.IsNaN() = false
NaN.IsNaN() = true
Cum se compară valorile NaN?
Fiecare valoare NaN este considerată distinctă. Aceasta înseamnă că niciun NaN nu este egal cu niciun alt NaN. Prin acest principiu, dacă comparați o valoare cu alta, rezultatul este întotdeauna negativ. Deoarece NaN este neordonat, deci o comparație numerică care implică chiar și un singur NaN returnează fals. Java oferă Float.NaN și Double.NaN pentru câmpurile constante din ambele clase pentru a efectua comparații. Le putem diferenția în două scenarii separate:- Adevărat: numai în caz de inegalitate (!=)
- Fals: pentru toți operanzii de comparație (==, <=, >=, <, >)
public class ComparingNaN
{ public static void main(String[] args)
{
// Comparing NaN values for Float constants
System.out.println (Float.NaN != Float.NaN); // true
System.out.println (Float.NaN == Float.NaN); // false
System.out.println (Float.NaN < Float.NaN); // false
System.out.println (Float.NaN > Float.NaN); // false
System.out.println (Float.NaN <= Float.NaN); // false
System.out.println (Float.NaN >= Float.NaN); // false
// Comparing NaN values for Float constants
System.out.println (Double.NaN != Double.NaN); // true
System.out.println (Double.NaN == Double.NaN); // false
System.out.println (Double.NaN < Double.NaN); // false
System.out.println (Double.NaN > Double.NaN); // false
System.out.println (Double.NaN <= Double.NaN); // false
System.out.println (Double.NaN >= Double.NaN); // false
}
}
Cum se generează valori NaN?
Înainte de a încheia, să ne uităm la câteva exemple comune de obținere a unui Not a Number (nan).
public class GenerateNaNValues {
static final float ZERO = 0;
public static void main (String[]args)
{
System.out.println("ZERO / ZERO = " + (ZERO / ZERO));
System.out.println("+INFINITY - INFINITY = " +
(Float.POSITIVE_INFINITY + Float.NEGATIVE_INFINITY));
System.out.println("-INFINITY * ZERO = " + (Float.NEGATIVE_INFINITY * ZERO));
System.out.println("+INFINITY * ZERO = " + (Float.POSITIVE_INFINITY * ZERO));
System.out.println("log10(-10) = " + Math.log(-10));
System.out.println("√-10 = " + Math.sqrt(-10));
System.out.println("NaN + 10 = " + (Float.NaN + 10));
System.out.println("NaN - 10 = " + (Float.NaN - 10));
System.out.println("NaN * 10 = " + (Float.NaN * 10));
System.out.println("NaN / 10 = " + (Float.NaN / 10));
System.out.println("NaN + NaN = " + (Float.NaN + Float.NaN));
System.out.println("NaN - NaN = " + (Float.NaN - Float.NaN));
System.out.println("NaN * NaN = " + (Float.NaN * Float.NaN));
System.out.println("NaN / NaN = " + (Float.NaN / Float.NaN));
}
}
Ieșire:
ZERO / ZERO = NaN
+INFINITY - INFINITY = NaN
-INFINITY * ZERO = NaN
+INFINITY * ZERO = NaN
log10(-10) = NaN
√-10 = NaN
NaN + 10 = NaN
NaN - 10 = NaN
NaN * 10 = NaN
NaN / 10 = NaN
NaN + NaN = NaN
NaN - NaN = NaN
NaN * NaN = NaN
NaN / NaN = NaN
GO TO FULL VERSION