Hogyan generáljunk véletlen számot Java
⚡ Okos összefoglaló
Véletlenszerű számok Java négy kapcsolódó szabványos könyvtári opcióból származnak: a Random osztályból, a Math.randomból, a ThreadLocalRandomból és a SecureRandomból, amelyek mindegyike a sebesség, a szálbiztonság és a kriptográfiai erősség eltérő keverékét fedi le valós alkalmazásokhoz.

Véletlenszerű számok jelennek meg mindenhol Java, az egységtesztelési adatoktól és a kockadobásos játékoktól kezdve a munkamenet-tokenekig és a kevert paklikig. Ez az oktatóanyag elmagyarázza, hogyan generálhatunk véletlenszámokat a Java a standard könyvtár összes opciójának használata, és a feladathoz megfelelő kiválasztása.
Véletlenszám generálása Java
Az Java A standard könyvtár négy gyakori módszert kínál véletlenszámok generálására:
java.util.Randomaz általános célú osztály. Boolean, int, long, float és double értékeket állít elő olyan metódusok segítségével, mint anextInt,nextLongésnextDouble.Math.randomegy statikus segédfüggvény, amely egy megosztott függvényt használva 0.0 (beleértve) és 1.0 (kizárva) közötti dupla értéket ad vissza.Randombelsőleg.ThreadLocalRandominjava.util.concurrentminden szálnak saját generátort ad, így több szál nem verseng egyetlen példányon belül.SecureRandominjava.securitykriptográfiailag erős pszeudovéletlenszerű számokat állít elő jelszavakhoz, munkamenet-azonosítókhoz és kulcsokhoz.
Az alábbi szakaszok bemutatják, hogyan generálhatunk tíz véletlenszámot az egyes megközelítésekkel.
Példa: Véletlenszám generálása Java Véletlen osztály
Az első példa a következőt használja: java.util.Random tíz egész szám előállítása 0 és 99 között:
import java.util.Random; public class RandomNumbers { public static void main(String[] args) { Random objGenerator = new Random(); for (int iCount = 0; iCount < 10; iCount++) { int randomNumber = objGenerator.nextInt(100); System.out.println("Random No : " + randomNumber); } } }
output:
Random No : 17 Random No : 57 Random No : 73 Random No : 48 Random No : 68 Random No : 86 Random No : 34 Random No : 97 Random No : 73 Random No : 18
Egy példa Random úgy jön létre, mint objGenerator Az nextInt(int bound) A metódus egy 0 (beleértve) és a megadott korlát (kizáró) közötti értéket ad vissza, tehát nextInt(100) 0 és 99 közötti értékeket ad vissza. A sorozat reprodukálhatóvá tételéhez adjunk át egy seedet a konstruktornak, például new Random(42)ugyanaz a vetőmag mindig ugyanazt a szekvenciát eredményezi, ami hasznos tesztekben és szimulációkban.
Példa: Használata Java Math.random
Tíz véletlenszerű érték generálásához 0.0 és 1.0 között, hívjuk meg a statikus függvényt Math.random módszer egy belül hurokEz a leggyorsabb módja annak, hogy véletlenszerű dupla értéket kapjunk generátor objektum létrehozása nélkül:
public class DemoRandom { public static void main(String[] args) { for (int xCount = 0; xCount < 10; xCount++) { System.out.println(Math.random()); } } }
output:
0.46518450373334297 0.14859851177803485 0.5628391820492477 0.6323378498048606 0.1740198445692248 0.9140544122258946 0.9167350036262347 0.49251219841030147 0.7426056725722353 0.2039418871298877
a motorháztető alatt, Math.random egyetlen statikus elemet hoz létre Random első használatkor és híváskor nextDouble rajta. Ez az egyetlen megosztott generátor megfelelő a demókhoz, de szűk keresztmetszetet képez nagy többszálú terhelés alatt, amit a következő szakaszok tárgyalnak.
Véletlenszerű szám generálása egyéni tartományban
A valódi programok általában egy adott tartományon belüli véletlenszerű értékre szorulnak, például egy 1 és 6 közötti egész számra egy kockadobáshoz, vagy egy 10.0 és 20.0 közötti dupla értékre egy szimulációhoz. Két minta szinte minden esetet lefed.
Véletlenszerű egész szám a minimum és a maximum között (beleértve):
import java.util.Random; public class RangeDemo { public static void main(String[] args) { Random rnd = new Random(); int min = 1; int max = 6; // nextInt(max - min + 1) returns 0..(max-min), then shift by min int dice = rnd.nextInt(max - min + 1) + min; System.out.println("Dice roll : " + dice); } }
Véletlenszerű dupla a min és max között:
double min = 10.0; double max = 20.0; double value = min + (max - min) * Math.random(); System.out.println("Value : " + value);
Mindkét minta úgy működik, hogy a generátor natív tartományából vesz egy értéket, azt a céltartomány szélességére méretezi, majd a minimummal felfelé tolja el. Ha bekapcsolva van Java 8-as vagy újabb verzió esetén ugyanaz az eredmény érhető el az újabb verzión keresztül is. ints, longsés doubles stream metódusok bekapcsolva Random, Például rnd.ints(10, 1, 7).forEach(System.out::println) tíz kockadobásért.
ThreadLocalRandom többszálú feldolgozáshoz Code
Egyetlen megosztott Random szálbiztos, de versengés esetén lassú, mivel minden szálnak ugyanazon a belső magon kell szinkronizálódnia. ThreadLocalRandom, hozzáadva Java 7 éves és ott lakik java.util.concurrent, minden szálnak saját generátort ad, így nincs zárolási versengés.
import java.util.concurrent.ThreadLocalRandom; public class ThreadLocalDemo { public static void main(String[] args) { // random int in [1, 100] int i = ThreadLocalRandom.current().nextInt(1, 101); // random long in [1000, 5000] long l = ThreadLocalRandom.current().nextLong(1000L, 5001L); // random double in [0.0, 1.0) double d = ThreadLocalRandom.current().nextDouble(); System.out.println(i + " " + l + " " + d); } }
Felhasználás ThreadLocalRandom.current() munkaszálakon, párhuzamos adatfolyamokon és bármely egyidejű feladaton belül. Vegye figyelembe, hogy setSeed dob UnsupportedOperationException, tehát a reprodukálhatóság érdekében történő seedelés nem támogatott; ha fix seedre van szüksége, maradjon a sima Random.
SecureRandom a biztonság szempontjából érzékeny véletlenszerűségekhez Numbers
Példányai Random és a ThreadLocalRandom nem kriptográfiailag biztonságosak. Néhány kimeneti minta alapján a támadó rekonstruálhatja a belső állapotot és megjósolhatja a jövőbeli értékeket. Jelszavakhoz, munkamenet-tokenekhez, sóértékekhez és kriptográfiai kulcsokhoz használja a következőt: java.security.SecureRandom ehelyett. Az operációs rendszer entrópiakészletéből merít alapanyagot, és olyan értékeket hoz létre, amelyek ellenállnak a predikciónak.
import java.security.SecureRandom; public class SecureDemo { public static void main(String[] args) { SecureRandom secure = new SecureRandom(); byte[] token = new byte[16]; secure.nextBytes(token); // 128-bit random token int otp = secure.nextInt(1_000_000); // 6-digit one-time code System.out.println("OTP : " + String.format("%06d", otp)); } }
SecureRandom lassabb, mint Random mert erősebb algoritmusokat és gazdagabb alapanyagot használ. Tartsd fenn biztonsági munkákhoz, és használd a gyorsabb generátorokat játékokhoz, szimulációkhoz és tesztadatokhoz.
