Comment puis-je générer des entiers aléatoires dans une gamme spécifique en Java?
Comment puis-je générer un hasard int
valeur dans une plage spécifique?
J'ai essayé ce qui suit, mais ceux qui ne travaillent pas:
Tentative 1:
randomNum = minimum + (int)(Math.random() * maximum);
//Bug: `randomNum` can be bigger than `maximum`.
Tentative 2:
Random rn = new Random();
int n = maximum - minimum + 1;
int i = rn.nextInt() % n;
randomNum = minimum + i;
//Bug: `randomNum` can be smaller than `minimum`.
Vous devez vous connecter pour publier un commentaire.
Dans Java 1.7 ou plus tard, le standard de la façon de le faire est comme suit:
Voir pertinentes de la JavaDoc. Cette approche a l'avantage de ne pas avoir à initialiser explicitement un java.util.Aléatoire instance, qui peut être une source de confusion et d'erreur, si elle est utilisée de façon inappropriée.
Cependant, à l'inverse il n'y a aucun moyen de définir explicitement la graine de sorte qu'il peut être difficile de reproduire les résultats dans des situations où c'est utile comme test ou de l'enregistrement du jeu des états ou similaire. Dans ces situations, la pré-Java 1.7 technique décrite ci-dessous peut être utilisé.
Avant de Java 1.7, le standard de la façon de le faire est comme suit:
Voir pertinentes de la JavaDoc. Dans la pratique, la java.util.Aléatoire classe est souvent préférable de java.lang.Les mathématiques.random().
En particulier, il n'est pas nécessaire de réinventer la entier aléatoire de la génération de la roue quand il y a une simple API au sein de la bibliothèque standard pour accomplir la tâche.
max
valeur estInteger.MAX_VALUE
il est possible de débordement ,résultant en unjava.lang.IllegalArgumentException
. Vous pouvez essayer avec :randInt(0, Integer.MAX_VALUE)
. Aussi, sinextInt((max-min) + 1)
retourne la plus grande valeur (assez rare, je suppose) de ne pas déborder de nouveau( en supposant que min et max sont assez élevés valeurs)? Comment faire face à ce genre de situations?RANDOM
classe prend en chargenextLong
. Vous pourriez utiliser à la place denextInt
pour les longues.double
. Juste pour:long val = ((long) (r.nextDouble() * (max - min))) + min
ThreadLocalRandom.current().nextInt(min, max)
.ThreadLocalRandom.current().nextBytes(chunk);
si vous voulez vous éviter lanew Random()
. Grâce à vraiment une question populaire sur la génération aléatoire d'Entiers en Java.Noter que cette approche est plus biaisé et moins efficace qu'un
nextInt
approche, https://stackoverflow.com/a/738651/360211Un modèle standard pour la réalisation de ce est:
La Java bibliothèque de Mathématiques de la fonction Math.random() génère une valeur double de la gamme
[0,1)
. De l'avis de cette gamme ne comprend pas le 1.Afin d'obtenir une plage spécifique de valeurs d'abord, vous devez multiplier par l'ampleur de l'intervalle de valeurs que vous voulez couvrir.
Elle retourne une valeur dans la plage
[0,Max-Min)
, où "Max-Min" n'est pas inclus.Par exemple, si vous voulez
[5,10)
, vous avez besoin pour couvrir cinq valeurs entières si vous utilisezCe serait retourner une valeur dans la gamme
[0,5)
, où la 5 n'est pas inclus.Maintenant, vous avez besoin de modifier cette plage jusqu'à la plage que vous ciblez. Vous le faire en ajoutant de la valeur Min.
Maintenant, vous obtiendrez une valeur dans la gamme
[Min,Max)
. À la suite de notre exemple, cela signifie que[5,10)
:Mais, ce n'est toujours pas inclure
Max
et vous obtenez une valeur de type double. Afin d'obtenir leMax
inclus dans la valeur, vous avez besoin pour ajouter 1 pour votre gamme de paramètre(Max - Min)
et puis tronquer la partie décimale par un casting pour un int. Ceci est réalisé via:Et là vous l'avez. Une valeur entière aléatoire dans la plage
[Min,Max]
, ou par l'exemple[5,10]
:Utilisation:
L'entier
x
est maintenant le nombre aléatoire qui a un résultat possible de5-10
.Utilisation:
Avec java-8 ils ont introduit la méthode
ints(int randomNumberOrigin, int randomNumberBound)
dans leau Hasard
classe.Par exemple, si vous souhaitez générer des cinq entiers aléatoires (ou un seul) dans l'intervalle [0, 10], il suffit de faire:
Le premier paramètre indique juste la taille de la
IntStream
généré (ce qui est la méthode surchargée de celui qui produit un nombre illimité deIntStream
).Si vous avez besoin de faire de multiples appels distincts, vous pouvez créer une infinité de primitives itérateur à partir du flux:
Vous pouvez aussi le faire pour
double
etlong
valeurs.Espère que cela aide! 🙂
streamSize
- le premier paramètre de cette méthode étant donnéstreamSize !=0
. Quelle est la différence sistreamSize
1/2/n est-il donné?Vous pouvez modifier votre deuxième exemple de code:
Juste une petite modification de votre première solution serait suffisante.
Voir plus ici pour la mise en œuvre de
au Hasard
La
Math.Random
classe dans Java est basée sur 0. Ainsi, si vous écrivez quelque chose comme ceci:x
sera entre0-9
inclusive.Donc, étant donné le tableau suivant de
25
articles, le code pour générer un nombre aléatoire entre0
(la base de la matrice) etarray.length
serait:Depuis
i.length
sera de retour25
, lenextInt( i.length )
sera de retour un numéro entre la gamme de0-24
. L'autre option est d'aller avecMath.Random
qui fonctionne de la même manière.Pour une meilleure compréhension, découvrez post sur le forum Intervalles aléatoires (archive.org).
index
variable ne sera pas affecter le résultat de nombres aléatoires. Vous pouvez choisir d'initialiser, de quelque manière que vous le souhaitez sans avoir à vous soucier de changer l'issue. Espérons que cette aide.int index = rand.nextInt(i.Length);
int index; \n index = rand...
si l'on est friand des déclarations et des affectations sur des lignes différentes. Certaines normes de codage sont plus strictes (et sans raison apparente) que d'autres.ThreadLocalRandom équivalent de la classe java.util.Aléatoire pour l'environnement multithread. Générer un nombre aléatoire est effectué localement dans chacun des threads. Si nous avons une meilleure performance en réduisant les conflits.
x,y - intervalles, par exemple, (1,10)
Me pardonner d'être fastidieux, mais la solution proposée par la majorité, c'est à dire,
min + rng.nextInt(max - min + 1))
, semble périlleux en raison du fait que:rng.nextInt(n)
ne peut pas atteindreInteger.MAX_VALUE
.(max - min)
peut provoquer un débordement lors de lamin
est négatif.À toute épreuve solution serait de retour des résultats corrects pour tout
min <= max
dans [Integer.MIN_VALUE
,Integer.MAX_VALUE
]. Considérez les points suivants implémentation naïve:Bien qu'inefficace, remarque que la probabilité de succès dans le
while
boucle sera toujours de 50% ou plus.Il peut être fait simplement en faisant la déclaration suivante:
Ci-dessous est son code source
Randomizer.java
Il est tout propre et simple.
Je me demande si le nombre aléatoire générant des méthodes fournies par un Apache Commons Mathématiques bibliothèque devrait adapter le projet de loi.
Par exemple:
RandomDataGenerator.nextInt
ouRandomDataGenerator.nextLong
Prenons un exemple.
Supposons que je souhaite générer un nombre entre 5-10:
Nous comprenons ce...
Générer un nombre aléatoire pour la différence de min et max à l'aide de la nextint(n) méthode, puis ajouter min nombre au résultat:
Joshua Bloch. Efficace Java. Troisième Édition.
À partir de Java 8
Pour fourche de rejoindre les piscines et les filières parallèles, l'utilisation
SplittableRandom
qui est généralement plus rapide, une meilleure indépendance statistique et de l'homogénéité des propriétés en comparaison avecRandom
.À la génération aléatoire
int
dans la gamme[0, 1_000]:
À la génération aléatoire
int[100]
tableau de valeurs dans la gamme[0, 1_000]:
Retourner un Flux de valeurs aléatoires:
.parallel()
? Il me semble que la génération d'un 100 nombres aléatoires serait trop trivial pour justifier le parallélisme.parallel
de traitement). Par ailleurs, pour le tableau de1_000_000
éléments, laparallel
version a été 2 fois plus vite sur ma machine en comparaison avec séquentielle.Cette méthode pourrait être pratique à utiliser:
Cette méthode retourne un nombre aléatoire entre fourni des valeurs min et max:
et cette méthode retourne un nombre aléatoire de fourni des valeurs min et max (si le nombre généré peut être aussi le min ou le max nombre):
// Since the random number is between the min and max values, simply add 1
. Pourquoi? Ne pas min comte? En général, la plage est [min, max) où min est inclus et max est exclue. Mauvaise réponse, voté contre.min + 1
sera deux fois plus susceptibles que les autres de nombre à la suite degetRandomNumberBetween
!Voici une classe pour générer de l'aléatoire
ints
dans une gamme avec n'importe quelle combinaison de inclusif/exclusif limites:En cas de rouler des dés, il serait nombre aléatoire entre 1 à 6 (et non de 0 à 6), donc:
Pour générer un nombre aléatoire "entre deux nombres", utilisez le code suivant:
Cela vous donne un nombre aléatoire entre 1 (inclus) et 11 (exclusif), afin d'initialiser la upperBound valeur par l'ajout de 1. Par exemple, si vous souhaitez générer des nombre aléatoire entre 1 à 10 puis initialiser le upperBound nombre de 11 au lieu de 10.
Ou de prendre un coup d'oeil à RandomUtils de Apache Commons.
Double.valueOf(Math.random()*(maximum-minimun)).intValue()
est assez obscure (et inefficace) pour dire(int)(Math.random()*(maximum-minimun))
...Suffit d'utiliser la Aléatoire classe:
Vous pouvez le faire de façon concise dans Java 8:
J'ai trouvé cet exemple Générer des nombres aléatoires :
Cet exemple génère des entiers aléatoires dans une plage spécifique.
Un exemple de fonctionnement de cette classe :
Lorsque vous avez besoin de beaucoup de nombres aléatoires, je ne recommande pas l'Aléatoire de la classe dans l'API. Il a juste une trop petite période. Essayez le Mersenne twister à la place. Il est une implémentation de Java.
Une autre option est seulement à l'aide de Apache Commons:
J'utilise ceci:
Vous pouvez le convertir en un Entier si vous le souhaitez.
new Random
(consultez la JavaDoc): "Crée un nouveau générateur de nombre aléatoire. Ce constructeur définit la graine du générateur de nombres aléatoires à une valeur très susceptibles d'être distinct de tout autre invocation de ce constructeur." Très probablement peut simplement impliquer l'utilisation de l'heure actuelle en tant que semences. Si cette fois, utilise les millisecondes puis les ordinateurs actuels sont assez rapides pour générer le même nombre. Mais, outre que 2147483647 estInteger.MAX_VALUE
; la sortie dépend évidemment de l'entrée que vous n'avez pas spécifié.Voici un exemple simple qui montre comment générer des nombre aléatoire à partir de fermé
[min, max]
gamme, tandis quemin <= max is true
Vous pouvez le réutiliser en tant que champ dans le trou de la classe, ayant également tous les
Random.class
méthodes dans un endroitExemple de résultats:
Sources:
Il est préférable d'utiliser SecureRandom plutôt qu'un simple Hasard.
private static int SecureRandom rand = new SecureRandom();
2:static {
3:rand.setSeed(...);
4:}
SecureRandom
, il sera classé par le système. En appelant directementsetSeed
est très dangereux, il peut remplacer le (très aléatoire) de la graine avec la date. Et qui va certainement pas résultat dans unSecureRandom
, comme n'importe qui peut deviner le temps et d'essayer et de graines de leur propreSecureRandom
exemple avec cette information.Cela fonctionne bien.
OU
Vous pouvez utiliser ce bout de code qui permettra de résoudre votre problème:
Utilisation myRandomNumber (qui vous donnera un nombre dans une fourchette).
Vous pouvez faire quelque chose comme ceci:
Je vais simplement indiquer quel est le problème avec les solutions fournies par la question et pourquoi les erreurs.
Solution 1:
Problème: randomNum est affecté des valeurs de nombre plus grand que le maximum.
Explication: Supposons que notre minimum est de 5, et le maximum est de 10. N'importe quelle valeur de
Math.random()
supérieure à 0,6 fera l'expression d'évaluer à 6 ou plus, et l'ajout de 5 le rend supérieur à 10 (maximum). Le problème est que vous êtes en multipliant le nombre aléatoire par le maximum (ce qui génère un nombre presque aussi grand que le maximum), puis en ajoutant le minimum. À moins que le minimum est de 1, ce n'est pas correct. Vous devez passer à l', comme mentionné dans d'autres réponsesLe +1 est parce que
Math.random()
ne reviendra jamais 1.0.Solution 2:
Votre problème ici est que les '%' peut renvoyer un nombre négatif si le premier terme est plus petit que 0. Depuis
rn.nextInt()
renvoie des valeurs négatives avec ~50% de chance, vous pourrez également ne pas obtenir le résultat escompté.Ce, a été, cependant, presque parfait. Vous venez d'avoir à regarder un peu plus bas dans la Javadoc, nextInt(int n). Avec cette méthode, en faisant
Serait également retourner le résultat souhaité.
Une approche différente à l'aide de Java 8 IntStream et des Collections.shuffle
L'équivalent en Scala
List<Integer> ls = range.boxed().collect(Collectors.toList());
Vous pouvez utiliser
méthode qui est de apache commons.
Je pense à linéairement normaliser les nombres aléatoires générés dans la plage désirée à l'aide de la suite. Laissez
x
être un nombre aléatoire, laisseza
etb
être minimale et maximale de la plage de numéro normalisé.Puis ci-dessous est juste un code très simple snipplet pour tester la gamme de produits par la cartographie linéaire.
Je viens de générer un nombre aléatoire à l'aide des Mathématiques.random() et de le multiplier par un grand nombre, disons 10000. Donc, je reçois un nombre entre 0 à 10 000 et appeler ce numéro
i
. Maintenant, si j'ai besoin de chiffres entre (x, y), puis effectuez les opérations suivantes:Donc, tous les
i
's sont des nombres compris entre x et y.Pour supprimer les biais comme l'a souligné dans les commentaires, plutôt que de multiplier par 10000 (ou le grand nombre), de le multiplier par (y-x).
Vous pouvez également utiliser
Cependant, cette classe ne fonctionne pas bien dans un environnement multi-thread.
Faire la modification suivante dans Tentative 1 devrait faire le travail -
Vérifier cette pour code de travail.
Code suivant peut être utilisé:
ThreadLocalRandom
. Si une question a été protégée, alors s'il vous plaît, prenez soin de ne pas dupliquer les réponses.Un de mes amis m'avait demandé la même question dans l'université d'aujourd'hui (ses exigences était de générer un nombre aléatoire entre 1 & -1). J'ai donc écrit ceci, et il fonctionne très bien jusqu'à présent avec mes tests. Il y a dans l'idéal, un grand nombre de façons de générer des nombres aléatoires donné une fourchette. Essayez ceci:
Fonction:
Exécuter comme ceci:
Je pense que ce code fonctionne pour elle. Veuillez essayer ceci:
Vous pouvez soit utiliser le Hasard de classe pour générer un nombre aléatoire et ensuite utiliser .nextInt(maxNumber) pour générer un nombre aléatoire. Le maxNumber est le nombre que vous voulez le maximum lors de la génération d'un nombre aléatoire. Rappelez-vous toutefois, que le Hasard de classe vous donne les chiffres de 0 à maxNumber-1.
Une autre façon de le faire est d'utiliser les Mathématiques.Random() de la classe dont le nombre de classes dans les écoles exigent que vous utilisez, car il est plus efficace et vous n'avez pas à déclarer un nouvel objet Aléatoire. Pour obtenir un nombre aléatoire à l'aide des Mathématiques.Random() vous tapez:
Cela va générer nombres Aléatoires liste avec gamme (Min - Max) avec aucun duplicata.
Ajouter cette méthode.
Espère que cela va vous aider.
J'ai créé une méthode pour obtenir un entier unique dans une plage donnée.
Si vous utilisez déjà
Commons Lang API 2.x
ou la dernière version puis il y a une classe pour la génération de nombre aléatoireRandomUtils
.Renvoie une pseudo-aléatoire de distribution uniforme int valeur entre 0 (inclus) et la valeur spécifiée (exclusif), de la Mathématique.random() de la séquence.
Paramètres:
n - spécifié exclusif max-valeur
Remarque: Dans RandomUtils ont beaucoup de méthodes pour la génération de nombre aléatoire
Voici un autre exemple d'utilisation de l'Aléatoire et de la forEach
Dites que vous voulez une fourchette entre 0 à 9, 0 est le minimum et 9 est maximale. Ci-dessous la fonction imprimer quoi que ce soit entre 0 et 9. Il en va de même pour toutes les gammes.
Le code ci-dessous génère un nombre aléatoire compris entre 100 000 et 900 000. Ce code génère des six valeurs numériques. Je suis en utilisant ce code pour générer un à six chiffres BDP.
Utilisation
import java.util.Random
pour utiliser cette méthode aléatoire.C'est le moyen facile de le faire.
Dans il 5 est le point de départ de nombres aléatoires. 6 la gamme, y compris le nombre 5.
Essayez d'utiliser
org.apache.commons.lang.RandomStringUtils
classe. Oui, c'parfois donner un certain nombre adjacente, mais il donnera la valeur entre 5 et 15:Nombre aléatoire de l'intervalle [min..max] inclusive:
Plus de ci-dessus suggestion ne pas envisager de "débordement", Par exemple: min = Integer.MIN_VALUE, max = 100. L'un de correct approches j'ai jusqu'à présent est:
Il y a une bibliothèque à https://sourceforge.net/projects/stochunit/ pour la manipulation de sélection de plages.
Il a bord d'inclusion/exclusion.
Utiliser java.util pour Aléatoire pour un usage général.
Vous pouvez définir la plage minimale et maximale pour obtenir ces résultats.
Un moyen simple de générer des n nombres aléatoires entre a et b
e.g a =90 b=100, n =20
r.ints()
retourne unIntStream
et a plusieurs méthodes utiles, un coup d'oeil à son API.À L'Aide De Java 8 Ruisseaux,
Il génère des nombres de 1-Randombound dans cet exemple.
voici une fonction qui retourne exactement un nombre entier nombre aléatoire dans une plage définie par
lowerBoundIncluded
etupperBoundIncluded
, comme demandé par user42155SplittableRandom splittableRandom = new SplittableRandom();
randomInt.apply( …, … ); //gets the random number
...ou plus courte pour le temps de génération d'un nombre aléatoire
Ci-dessous est un exemple qui montre comment générer des entiers aléatoires dans une plage spécifique. Attribuer la valeur que vous souhaitez que la valeur maximale de la variable " max " et attribuer la valeur que vous souhaitez que la valeur minimale de la variable 'min'.
Utilisation
math.random()
et de définir les exigences de l'instruction if. La solution la plus simple et la plus rapide de l'approche