Twitter iPhone pliant OnePlus 11 PS5 Disney+ Orange Livebox Windows 11

supprimer des valeurs numeriques identiques

9 réponses
Avatar
osiris
Bonjour =E0 tous,

Je vous explique mon probleme, je veux une liste de 32 nombres (avec
des chiffres compris de 1 =E0 60).

Le probleme c'est que dans cette liste je retrouve des nombres
identiques, ce que je ne veux pas.
Mon script bien sur ne fonctionne pas vraiment car je ne teste que le
chiffre precedent si il est identique je relance un nombre pseudo
aleatoire

Quelques pourrait m'aider ??

merci beaucoup

Voici mon script

#!/usr/bin/perl -w

use strict;

print "les participants sont\n";
my @nombres;
for(my $j =3D 0; $j < 32; $j++) {
$nombres[$j] =3D int(rand(60) + 1);

if ($nombres[$j]=3D=3D$nombres[$j-1]) {
$nombres[$j] =3D int(rand(60) + 1);
print "$nombres[$j]\n";
} else {
print "$nombres[$j]\n";
}
}

Merci de vos reponses

Osiris73

9 réponses

Avatar
Paul Gaborit
À (at) 19 Jul 2005 04:49:25 -0700,
"osiris" écrivait (wrote):
Je vous explique mon probleme, je veux une liste de 32 nombres (avec
des chiffres compris de 1 à 60).


Vous voulez choisir au hasard 32 éléments parmi 60. Une méthode simple
à mettre en oeuvre est la suivante : mélanger un tableau contenant les
60 éléments puis ne prendre que les 32 premiers.

En utilisant le module List::Util :
----------------------------------------
use List::Util qw/shuffle/;

my @nombres = (shuffle 1..60)[0..31];
----------------------------------------

Si vous ne voulez pas utiliser List::Util, une subroutine shuffle
(fisher_yates_shuffle) est disponible dans la FAQ :

perldoc -q shuffle

Ce qui donne alors :
----------------------------------------
# fisher_yates_shuffle( @array ) :
# generate a random permutation of @array in place
sub fisher_yates_shuffle {
my $array = shift;
my $i;
for ($i = @$array; --$i; ) {
my $j = int rand ($i+1);
@$array[$i,$j] = @$array[$j,$i];
}
}

my @elements = 1..60;
fisher_yates_shuffle(@elements);
my @nombres = @elements[0..31];
----------------------------------------

--
Paul Gaborit - <http://perso.enstimac.fr/~gaborit/>
Perl en français - <http://perl.enstimac.fr/>

Avatar
Stephane Zuckerman
Bonjour,

Je vous explique mon probleme, je veux une liste de 32 nombres (avec
des chiffres compris de 1 à 60).

Le probleme c'est que dans cette liste je retrouve des nombres
identiques, ce que je ne veux pas.

#!/usr/bin/perl -w

use strict;

print "les participants sontn";
my @nombres;
for(my $j = 0; $j < 32; $j++) {
$nombres[$j] = int(rand(60) + 1);

if ($nombres[$j]==$nombres[$j-1]) {
$nombres[$j] = int(rand(60) + 1);
print "$nombres[$j]n";
} else {
print "$nombres[$j]n";
}
}


J'utiliserais un hash pour ce travail si j'étais vous.

Comme ça, j'ai l'assurance d'avoir l'unicité de mes valeurs, et le test se
ferait tant que le nombre de clés du hash n'est pas égal à 32.

#!/usr/bin/perl
use strict;
use warnings;
my %nombres;

while( keys(%nombres) < 32 ) {
my $tmp = int(rand(60)+1)};
$nombres{tmp} = 1; # "true"
print "$tmpn";
}

my @nombres = sort(keys(%nombres));

--
"Je deteste les ordinateurs : ils font toujours ce que je dis, jamais ce
que je veux !"
"The obvious mathematical breakthrough would be development of an easy
way to factor large prime numbers." (Bill Gates, The Road Ahead)

Avatar
osiris
À (at) 19 Jul 2005 04:49:25 -0700,
"osiris" écrivait (wrote):
Je vous explique mon probleme, je veux une liste de 32 nombres (avec
des chiffres compris de 1 à 60).


Vous voulez choisir au hasard 32 éléments parmi 60. Une méthode sim ple
à mettre en oeuvre est la suivante : mélanger un tableau contenant les
60 éléments puis ne prendre que les 32 premiers.

En utilisant le module List::Util :
----------------------------------------
use List::Util qw/shuffle/;

my @nombres = (shuffle 1..60)[0..31];
----------------------------------------

Si vous ne voulez pas utiliser List::Util, une subroutine shuffle
(fisher_yates_shuffle) est disponible dans la FAQ :

perldoc -q shuffle

Ce qui donne alors :
----------------------------------------
# fisher_yates_shuffle( @array ) :
# generate a random permutation of @array in place
sub fisher_yates_shuffle {
my $array = shift;
my $i;
for ($i = @$array; --$i; ) {
my $j = int rand ($i+1);
@$array[$i,$j] = @$array[$j,$i];
}
}

my @elements = 1..60;
fisher_yates_shuffle(@elements);
my @nombres = @elements[0..31];
----------------------------------------

--
Paul Gaborit - <http://perso.enstimac.fr/~gaborit/>
Perl en français - <http://perl.enstimac.fr/>


Merci encore, super ça fonctionne !!!!


Avatar
damien guerin
Je trouve cette méthode bof, car il y aura toujours des itérations de
trop...
Avatar
damien guerin
On peut également faire :

%hash=();
$hash{1}="";
$hash{2}="";
...
@tab=keys(%hash);
print "les participants sontn";
my @nombres;
for(my $j = 0; $j < 32; $j++) {
$nb = int(rand($#tab) + 1);
$nombres[$j] = $tab[$nb];
remove hash{$tab[$nb]};
@tab=keys(%hash);
print "$nombres[$j]n";
}


Du coup le tableau contiendra toujours l'ensemble des valeurs possible
moins celles déjà sorties...
Avatar
Stephane Zuckerman
Je trouve cette méthode bof, car il y aura toujours des itérations de
trop...


Mmmh. J'essayais de garder l'esprit de sa solution en fait. Au final, la
"vraie" itération de trop, c'est l'obligation d'avoir à recopier toutes
les clés du hash dans un tableau en fin de script. Sinon, les itérations
en trop étaient inhérentes à la solution choisie par le PO :-)

--
"Je deteste les ordinateurs : ils font toujours ce que je dis, jamais ce
que je veux !"
"The obvious mathematical breakthrough would be development of an easy
way to factor large prime numbers." (Bill Gates, The Road Ahead)

Avatar
Paul Gaborit
À (at) 19 Jul 2005 07:03:01 -0700,
"damien guerin" écrivait (wrote):
On peut également faire :

%hash=();
$hash{1}="";
$hash{2}="";
...
@tab=keys(%hash);
print "les participants sontn";
my @nombres;
for(my $j = 0; $j < 32; $j++) {
$nb = int(rand($#tab) + 1);
$nombres[$j] = $tab[$nb];
remove hash{$tab[$nb]};
@tab=keys(%hash);
print "$nombres[$j]n";
}


Du coup le tableau contiendra toujours l'ensemble des valeurs possible
moins celles déjà sorties...


Heu... 'remove' s'écrit 'delete' en Perl...

Une autre méthode un peu similaire :

----------------------------------------
my @nombres;
{
my @all = 1..60;
foreach (1..32) {
push @nombres, splice @all, rand(@all), 1;
}
}

print "@nombresn";
----------------------------------------


--
Paul Gaborit - <http://perso.enstimac.fr/~gaborit/>
Perl en français - <http://perl.enstimac.fr/>

Avatar
damien guerin
Oui, c'est vrai pardon, je n'ai point fait attention... (j'étais
pressé ;) )
Mais j'avoue que ta 1ère méthode proposée fait plus la classe ;)
Avatar
Paul Gaborit
À (at) 19 Jul 2005 09:06:46 -0700,
"damien guerin" écrivait (wrote):
Mais j'avoue que ta 1ère méthode proposée fait plus la classe ;)


Elle est plus rapide à écrire... pas obligatoirement à exécuter !


--
Paul Gaborit - <http://perso.enstimac.fr/~gaborit/>
Perl en français - <http://perl.enstimac.fr/>