NaN בג'אווה

1. סקירה כללית

פשוט שים, NaN הוא ערך סוג נתונים מספרי המייצג "לא מספר".

במדריך מהיר זה, נסביר את NaN ערך ב- Java והפעולות השונות שיכולות לייצר או לערב ערך זה.

2. מה זה NaN?

NaN בדרך כלל מציין את התוצאה של פעולות לא חוקיות. לדוגמא, ניסיון לחלק אפס באפס הוא פעולה כזו.

אנו גם משתמשים NaN לערכים שלא ניתן לייצג. השורש הריבועי -1 הוא מקרה כזה, שכן אנו יכולים לתאר את הערך (אני) רק במספרים מורכבים.

תקן IEEE לחשבון נקודה צפה (IEEE 754) מגדיר את NaN ערך. ב- Java, סוגי הנקודות הצפות לָצוּף ו לְהַכפִּיל ליישם תקן זה.

Java מגדירה NaN קבועים של שניהם לָצוּף ו לְהַכפִּיל סוגים כמו לָצוּף.NaN ו- כפול. נא:

קבוע המחזיק ערך Not-a-Number (NaN) מהסוג כפול. זה שווה ערך לערך שהוחזר על ידי Double.longBitsToDouble (0x7ff8000000000000L). "

ו:

"קבוע המחזיק ערך Not-a-Number (NaN) מהסוג לצוף. זה שווה ערך לערך שהוחזר על ידי Float.intBitsToFloat (0x7fc00000). "

אין לנו קבועים מסוג זה עבור סוגי נתונים מספריים אחרים בג'אווה.

3. השוואות עם NaN

במהלך שיטות הכתיבה בג'אווה, עלינו לבדוק שהקלט תקף ובתחום הצפוי. NaN ערך אינו קלט חוקי ברוב המקרים. לכן עלינו לוודא שערך הקלט אינו a NaN ערך וטיפול בערכי קלט אלה כראוי.

NaN לא ניתן להשוות עם ערך סוג צף כלשהו. זה אומר שנקבל שֶׁקֶר לכל פעולות ההשוואה הכוללות NaN (למעט "! =" עבורו אנו מקבלים נָכוֹן).

אנחנו מקבלים נָכוֹן ל "x! = x ” אם ורק אם איקס הוא NaN:

System.out.println ("NaN == 1 =" + (NAN == 1)); System.out.println ("NaN> 1 =" + (NAN> 1)); System.out.println ("NaN <1 =" + (NAN NaN = "+ (NAN> NAN)); System.out.println (" NaN <NaN = "+ (NAN <NAN)); System.out. println ("NaN! = NaN =" + (NAN! = NAN)); 

בואו נסתכל על התוצאה של הפעלת הקוד לעיל:

NaN == 1 = שקר NaN> 1 = שקר NaN NaN = שקר NaN <NaN = שקר NaN! = NaN = נכון 

לָכֵן, אנחנו לא יכולים לבדוק NaN על ידי השוואה עם NaN באמצעות "==" או "! =". למעשה, לעתים נדירות עלינו להשתמש במפעילי "==" או "! =" עם לָצוּף אוֹ לְהַכפִּיל סוגים.

במקום זאת, אנו יכולים להשתמש בביטוי "איקס != x ”. ביטוי זה מחזיר נכון רק עבור NAN.

אנו יכולים גם להשתמש בשיטות Float.isNaN ו Double.isNaN כדי לבדוק אם קיימים ערכים אלה. זוהי הגישה המועדפת מכיוון שהיא קריאה ומובנת יותר:

כפול x = 1; System.out.println (x + "הוא NaN =" + (x! = X)); System.out.println (x + "הוא NaN =" + (Double.isNaN (x))); x = Double.NaN; System.out.println (x + "הוא NaN =" + (x! = X)); System.out.println (x + "הוא NaN =" + (Double.isNaN (x))); 

נקבל את התוצאה הבאה בעת הפעלת קוד זה:

1.0 הוא NaN = שקר 1.0 הוא NaN = שקר NaN הוא NaN = אמיתי NaN הוא NaN = נכון

4. הפקת מבצעים NaN

תוך כדי פעולות הקשורות לָצוּף ו לְהַכפִּיל סוגים, עלינו להיות מודעים ל NaN ערכים.

כמה שיטות ופעולות של נקודה צפה מייצרות NaN ערכים במקום לזרוק יוצא מן הכלל. ייתכן שנצטרך לטפל בתוצאות כאלה במפורש.

מקרה שכיח וכתוצאה מכך ערכים לא מספר הם פעולות מספריות לא מוגדרות מתמטיות:

כפול אפס = 0; System.out.println ("ZERO / ZERO =" + (ZERO / ZERO)); System.out.println ("INFINITY - INFINITY =" + (Double.POSITIVE_INFINITY - Double.POSITIVE_INFINITY)); System.out.println ("INFINITY * ZERO =" + (Double.POSITIVE_INFINITY * ZERO)); 

דוגמאות אלה מביאות לפלט הבא:

אפס / אפס = אינסוף NaN - אינסוף = אינסוף Na * אפס = NaN 

פעולות מספריות שאינן מביאות לתוצאות במספרים ממשיים מייצרות גם כן NaN:

System.out.println ("שורש ריבוע של -1 =" + Math.sqrt (-1)); System.out.println ("LOG OF -1 =" + Math.log (-1)); 

הצהרות אלה יביאו:

שורש ריבועי של -1 = NaN יומן של -1 = NaN 

כל הפעולות המספריות עם NaN כתוצרת אופרנד NaN כתוצאה:

System.out.println ("2 + NaN =" + (2 + Double.NaN)); System.out.println ("2 - NaN =" + (2 - Double.NaN)); System.out.println ("2 * NaN =" + (2 * Double.NaN)); System.out.println ("2 / NaN =" + (2 / Double.NaN)); 

והתוצאה של האמור לעיל היא:

2 + NaN = NaN 2 - NaN = NaN 2 * NaN = NaN 2 / NaN = NaN 

לבסוף, איננו יכולים להקצות ריק ל לְהַכפִּיל אוֹ לָצוּף משתני סוג. במקום זאת, אנו עשויים להקצות במפורש NaN למשתנים כאלה כדי לציין ערכים חסרים או לא ידועים:

maxValue כפול = Double.NaN;

5. מסקנה

במאמר זה דנו NaN והפעולות השונות הכרוכות בו. דנו גם בצורך לטפל NaN תוך כדי חישובי נקודות צפות בג'אווה במפורש.

קוד המקור המלא ניתן למצוא באתר GitHub.