Java >> Java tutorial >  >> Tag >> java.util

Genbrug af java.util.Random instans vs at oprette en ny instans hver gang

Det kommer an på.

Oprettelse af en enkelt instans er naturligvis enklere og bør være standardadfærden. Begge Random og SecureRandom er trådsikre, og vil derfor fungere fint. Gør først den enkle og korrekte ting, der virker, mål derefter din præstation i forhold til dit forventede peak-konflikt / peak perf-budget, og analyser resultaterne.

Random

Hvis du bruger Random og enkeltinstans-tilgangen er for langsom, overvej at bruge ThreadLocalRandom hvis det er muligt. JavaDoc'et i Random foreslår dens brug pænt:

Forekomster af java.util.Random er trådsikre. Men samtidig brug af den samme java.util.Random instans på tværs af tråde kan støde på uenighed og deraf følgende dårlig ydeevne. Overvej i stedet at bruge ThreadLocalRandom i flertrådede designs.

Det vil kun oprette en instans for hver tråd, der får adgang til den. Oprettelsesomkostningerne for en Random / ThreadLocalRandom instans er ikke sindssyg, men den er højere end oprettelsen af ​​et "normalt" objekt, så du bør nok undgå at oprette en ny instans for hver indkommende anmodning. At oprette en pr. tråd er generelt et godt sødt sted.

Jeg vil sige, at i moderne applikationer med poolede tråde, bør du næsten altid bruge ThreadLocalRandom i stedet for Random - tilfældigheden er den samme, men enkelttrådsydelsen er meget bedre.

SecureRandom

Hvis du bruger SecureRandom , dog ThreadLocalRandom er ikke en mulighed. Igen, gæt ikke, mål! Måske ved at bruge en enkelt delt forekomst af en SecureRandom vil være god nok. Test med din forventede højeste påstand, og hvis den sikre tilfældige instans viser sig at være en flaskehals, så tænk først på måder at forbedre situationen på.

Oprettelse af en SecureRandom instans er meget dyr, så du ønsker absolut ikke at oprette en for hver indkommende anmodning.

Afhængigt af din applikation, en ThreadLocal<SecureRandom> kan være en mulighed. Alligevel synes jeg, det er en overkill, og en ordning, der ligner Striped klasse (med X SecureRandom instanser, der er oprettet og tilfældigt tilgået for at hjælpe med at forhindre uenighed) kan foretrækkes.


Hvis du har brug for tilfældige tal til informationssikkerhed, er det kun en kryptografisk RNG (såsom java.security.SecureRandom) ) vil gøre. Og for enhver kryptografisk RNG er den enkleste tilgang kun at bruge én trådsikker forekomst af den for hele applikationen (bemærk at SecureRandom er trådsikker i henhold til dokumentationen); der er generelt ingen fordel ved at oprette flere forekomster af en kryptografisk RNG, da de alle i sidste ende skal initialiseres med højentropi ("uforudsigelige") data.

At indsamle sådanne "uforudsigelige" data er ikke trivielt, og i det mindste for din applikation behøver du ikke bekymre dig om det, når du bruger SecureRandom , som stort set gør dette for dig og inkluderer en setSeed metode, du kan bruge til at tilføje ekstra data for at supplere dets tilfældighed.


Java tag