1. Valós számok kerekítése

Amint már említettük, ha egy változóhoz valós számot rendelünk int, azt mindig a legközelebbi kisebb egész számra kerekítjük – a tört részt egyszerűen eldobjuk.

De könnyen elképzelhető egy olyan helyzet, amikor egy tört számot a legközelebbi egész számra kell kerekíteni bármelyik irányba, vagy akár felfelé is. Mit tesz ebben az esetben?

Erre és sok hasonló helyzetre a Java-nak van egy Mathosztálya, amely a round(), ceil(), és floor()metódusokkal rendelkezik.


Math.round()módszer

A Math.round()módszer egy számot a legközelebbi egész számra kerekít:

long x = Math.round(real_number)

De van itt még egy árnyalat: ez a metódus egész longszámot ad vissza (nem int). Mivel a valós számok nagyon nagyok lehetnek, a Java készítői úgy döntöttek, hogy a Java legnagyobb elérhető egész típusát használják: long.

Ennek megfelelően, ha egy programozó az eredményt egy változóhoz szeretné hozzárendelni int, akkor kifejezetten jeleznie kell a fordítónak, hogy elfogadja az esetleges adatvesztést (abban az esetben, ha a kapott szám nem fér bele egy inttípusba).

int x = (int) Math.round(real_number)

Példák:

Nyilatkozat Eredmény
int x = (int) Math.round(4.1);
4
int x = (int) Math.round(4.5);
5
int x = (int) Math.round(4.9);
5

Math.ceil()módszer

A Math.ceil()módszer egy számot egész számra kerekít. Íme, példák:

Nyilatkozat Eredmény
int x = (int) Math.ceil(4.1);
5
int x = (int) Math.ceil(4.5);
5
int x = (int) Math.ceil(4.9);
5

Math.floor()módszer

A Math.floor()módszer egy számot egész számra kerekít le . Íme, példák:

Nyilatkozat Eredmény
int x = (int) Math.floor(4.1);
4
int x = (int) Math.floor(4.5);
4
int x = (int) Math.floor(4.9);
4

Természetesen, ha egy számot egész számra kerekítünk, egyszerűbb egyszerűen egy type cast operátort használni:(int)

Nyilatkozat Eredmény
int x = (int) 4.9
4

Ha nehéz megjegyezni ezeket a neveket, egy rövid angol lecke segít:

  • Mathmatematikát jelent
  • Roundkereket jelent
  • Ceilingmennyezetet jelent
  • Floorpadlót jelent

2. Hogyan épülnek fel a lebegőpontos számok

A típus a és a doubleközötti tartományban tárolhat értékeket . Ez a hatalmas értéktartomány (a típushoz képest) azzal magyarázható, hogy a típus (valamint ) teljesen más belső szerkezettel rendelkezik, mint az egész típusok. Belsőleg a típus két számként kódolja az értékét: az elsőt mantisszának , a másodikat pedig kitevőnek hívják .-1.7*10308+1.7*10308intdoublefloatdouble

Tegyük fel, hogy megvan a szám 123456789, és tároljuk egy doubleváltozót. Amikor ezt megtesszük, a számot a rendszer konvertálja -ra , és belül a típus két számot tárol – és . A szignifikáns ("a szám jelentős része" vagy mantissza) pirossal, míg a kitevő kékkel van kiemelve.1.23456789*108double234567898

Ez a megközelítés lehetővé teszi nagyon nagy és nagyon kicsi számok tárolását. De mivel a számábrázolás 8 bájtra (64 bitre) korlátozódik, és a bitek egy részét a kitevő tárolására használják (valamint a mantissza előjelét és a kitevő előjelét), a mantissza ábrázolásához rendelkezésre álló maximális számjegyek a 15 .

Ez egy nagyon leegyszerűsített leírása a valós számok szerkezetének.


3. Pontosság elvesztése valós számokkal való munka során

Amikor valós számokkal dolgozik, mindig vegye figyelembe, hogy a valós számok nem pontosak . Mindig előfordulhatnak kerekítési és konverziós hibák , amikor decimálisról binárisra konvertálunk. Ezenkívül a leggyakoribb hibaforrás a pontosság elvesztése , amikor a számokat gyökeresen eltérő skálán adjuk össze/kivonjuk.

Ez utóbbi tény kissé elgondolkodtató a kezdő programozók számára.

Ha kivonunk -ból , akkor azt kapjuk .1/109109109

Számok kivonása gyökeresen eltérő skálákon Magyarázat
 1000000000.000000000;
-         0.000000001;
 1000000000.000000000;
A második szám rendkívül kicsi , ami miatt a jelentőségét (szürkével kiemelve) figyelmen kívül hagyja. A 15 jelentős számjegy narancssárga színnel van kiemelve.

Mit ne mondjak, a programozás nem azonos a matematikával.


4. Buktató a valós számok összehasonlításakor

Egy másik veszély leselkedik a programozókra, amikor valós számokat hasonlítanak össze. Valós számokkal való munka során merül fel, mert felhalmozódhatnak a kerekítési hibák. Az eredmény az, hogy vannak olyan helyzetek, amikor a valós számok egyenlőek, de nem. Vagy fordítva: a számok várhatóan eltérőek, de azonosak.

Példa:

Nyilatkozat Magyarázat
double a = 1000000000.0;
double b = 0.000000001;
double c = a - b;
A változó értéke a a következő lesz 1000000000.0
A változó értéke c : 1000000000.0
(a b változóban lévő szám túl kicsi)

A fenti példában aés cnem kell egyenlőnek lenniük, de vannak.

Vagy vegyünk egy másik példát:

Nyilatkozat Magyarázat
double a = 1.00000000000000001;
double b = 1.00000000000000002;
A változó értéke a lesz 1.0
A változó értéke b lesz1.0

5. Érdekes tény arrólstrictfp

A Java-nak van egy speciális strictfpkulcsszava ( strict f loating p oint ), amely más programozási nyelvekben nem található meg. És tudod miért van rá szükséged? Ez rontja a lebegőpontos számokkal végzett műveletek pontosságát. Íme a történet, hogyan alakult:

A Java készítői:
Nagyon szeretnénk, ha a Java rendkívül népszerű lenne, és a lehető legtöbb eszközön futna Java programok. Így gondoskodtunk arról, hogy a Java gép specifikációja szerint minden programnak ugyanúgy kell futnia minden típusú eszközön!
Az Intel processzorok gyártói:
Hello mindenki! Továbbfejlesztettük processzorainkat, és most minden valós szám 10 bájttal jelenik meg processzorainkon belül 8 bájt helyett. A több bájt több jelentős számjegyet jelent. Az mit jelent? Úgy van! Most még pontosabbak lesznek a tudományos számításai!
Tudósok és mindenki, aki részt vesz a rendkívül pontos számításokban:
Menő! Szép munka. Kiváló hír!
A Java készítői:
Nem-nem-nem, srácok! Korábban már elmondtuk, hogy minden Java programnak ugyanúgy kell futnia minden eszközön . Erőszakosan letiltjuk a 10 bájtos valós számok használatát az Intel processzoraiban.
Most megint minden rendben! Ne köszönjük meg.
Tudósok és mindenki, aki részt vesz a rendkívül pontos számításokban:
Teljesen megőrültél? Gyorsan állíts vissza mindent úgy, ahogy volt!
A Java készítői:
Srácok, ez a ti érdeketeket szolgálja! Képzelje csak el: minden Java program ugyanúgy fut minden eszközön . Ez nagyon jó!
Tudósok és mindenki, aki részt vesz a rendkívül pontos számításokban:
Nem. Egyáltalán nem menő. Gyorsan tegyen vissza mindent úgy, ahogy volt! Vagy tudja, hová helyezzük a Java-t?
A Java készítői:
Hmm. Miért nem mondtad azonnal? Természetesen visszatesszük.
Visszaállítottuk a legújabb processzorok összes funkciójának használatát.
Apropó... A strictfpkulcsszót külön is hozzáadtuk a nyelvhez. Ha egy függvény neve elé írod, akkor az adott függvényen belül minden valós számot tartalmazó művelet egyformán rossz lesz minden eszközön !