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

Pour se réveiller

33 réponses
Avatar
josephb
FU2 to fr.comp.sys.mac.programmation
Bonjour à tous,

Une pensée pour les sinistrés qui ont d'autres chats à fouetter que de
traîner sur Usenet.
Pour les autres habitués de focomosX, un petit casse-tête pour essayer
de réveiller les neurones engourdis.
Bon, je sais c'est de la programmation, d'où le suivi sur
fr.comp.sys.mac.programmation

Voilà le défi
Quelques mois de ça, il y a avait eu une enfilade assez nourrie à propos
du tirage du Loto.
Une des questions en rapport étant : la fonction aléatoire ("Random")
fournie par Applescript en standard, l'est-elle suffisamment, ou va-t-on
trouver certains nombres sortir significativement plus souvent que
d'autres ?

Pour tirer ça au clair, une seule manière : faire un très grand nombre
de tirages, disons 100 000, voire un million, plusieurs fois, et
comparer les occurences de chaque nombre sorti.

Donc la question lancée est : écrire le script (en pure AppleScript)
capable de faire ces 100 000 tirages, compter la sortie de chaque nombre
de 1 à 48 et le temps total mis pour ça. Le plus rapide (indépendamment
de la machine) a gagné.
Que des fonctions basiques d'AppleScript, rien d'ésotérique, pas de
commandes externes ou Shell.

Pour pimenter : je suis arrivé à un script qui, sur mon vénérable
MacPro, fait le boulot en 5" pour 100 000 tirages, après des versions
déjà très véloces qui mettaient respectivement 32" et 11" pour faire la
même chose. Peut-on encore améliorer la rapidité ?
Les futés, sont priés de s'affuter ;-)

"5 sec
1: 2102
2: 2089
3: 1990
4: 2072
5: 2085
6: 2152
7: 2032
8: 2040
9: 2073
10: 2087
11: 2120
12: 2097
13: 2095
14: 2114
15: 2046
16: 2145
17: 2052
18: 2073
19: 2106
20: 2132
21: 2092
22: 2032
23: 2079
24: 1990
25: 2025
26: 2117
27: 2045
28: 2118
29: 2038
30: 2082
31: 2073
32: 2108
33: 2031
34: 2168
35: 2137
36: 2091
37: 1998
38: 2147
39: 2029
40: 2116
41: 2146
42: 2105
43: 2099
44: 2096
45: 2084
46: 2113
47: 2111
48: 2028
--
J. B.

10 réponses

1 2 3 4
Avatar
olivier.marti
pehache wrote:
Le 05/06/2016 à 15:52, Joseph-B a écrit :
FU2 to fr.comp.sys.mac.programmation
Bonjour à tous,
Une pensée pour les sinistrés qui ont d'autres chats à fouetter que de
traîner sur Usenet.
Pour les autres habitués de focomosX, un petit casse-tête pour essayer
de réveiller les neurones engourdis.
Bon, je sais c'est de la programmation, d'où le suivi sur
fr.comp.sys.mac.programmation
Voilà le défi
Quelques mois de ça, il y a avait eu une enfilade assez nourrie à propos
du tirage du Loto.
Une des questions en rapport étant : la fonction aléatoire ("Random")
fournie par Applescript en standard, l'est-elle suffisamment, ou va-t-on
trouver certains nombres sortir significativement plus souvent que
d'autres ?
Pour tirer ça au clair, une seule manière : faire un très grand nombre
de tirages, disons 100 000, voire un million, plusieurs fois, et
comparer les occurences de chaque nombre sorti.

Il faudrait vraiment un très gros défaut dans le générateur pour que les
occurrences de chaque nombre devient de l'équiprobabilité. De plus tu
vas forcément trouver des déviations statistiques, qu'il va falloir
analyser pour savoir si elles sont normales ou pas.
Un défaut plus courant et plus difficile à mettre en évidence dans les
générateurs de nombres aléatoire ce sont les séquences prédictibles :
- par exemple 2 est suivi d'un 20, alors le générateur sort plus souvent
un 15 qu'autre chose en suivant.
- ou bien si un nombre quelconque sort au tirage N, alors il a plus de
chances de ressortir qu'un autre au tirage N+P

En fait le défaut des générateurs classiques à base de modulo est que
les nombres se retrouvent dans un nombre de plans limités quand on les
utilisent pour générer des n-uplets.
Le premier n-uplet est constitués des n premiers nombres tirés, puis le
second avec les suivant, etc ... Si n est grand, les nombres sont mals
répartis : ils se regroupent dans un nombre limités d'hypers plans
(dimensions n-1) au lieu d'être répartis de façon homogène dans l'espace
de dimension n.
Il faut des dimensions n assez grandes et tirer un très grand nombre de
n-uplet pour que ça pose un problème. Mais ça a amené à créer des
générateurs plus subtils pour certains problèmes de physique qui ont
besoin d'un très grand nombre de valeurs aléatoires.
Voir Marsaglia G (1968) Random numbers fall mainly in the planes. PNAS
61:25–28.
Je n'ai pas l'article sous la main, mais il me semble qu'avec un
générateur en 32 bits et n > 4 ou 5, il faut commencer à se méfier.
Avec un générateur 64 bits pour des valeurs uniques, tu peux tirer 100
000 nombres sans voir le problème.
Olivier
Avatar
michel.vauquois
Je vous souhaite bien le bonjour,
J'ai écrit il y a peu :
Je ne maîtrise pas ça du tout... mais je retiens la leçon.

Juste pour le fun...
Script modifié qui permet de choisir le nombre de nombres à tirer et le nombre de tirages à effectuer :
++++++++++
set myLoto to {}
set N to {text returned} of (display dialog "Combien de nombres à tirer ?" default answer 0 buttons {"OK"} default button 1)
set nbTirages to {text returned} of (display dialog "Combien de tirages à effectuer ?" default answer 0 buttons {"OK"} default button 1)
set t0 to (time of (current date)) --start timer
set listeCompt to {} -- liste des compteurs
repeat N times
copy 0 to the end of listeCompt
end repeat
repeat nbTirages times
set tempNb to random number from 1 to N
set item tempNb of listeCompt to ((item tempNb of listeCompt) + 1)
end repeat
repeat with j from 1 to N
set tempResultat to ("Le nombre " & j & " a été tiré " & item j of listeCompt & " fois.") as text
copy tempResultat to the end of myLoto
end repeat
set text item delimiters to {return}
set totalTime to ((time of (current date)) - t0) as string --stop timer
return ("Temps écoulé : " & totalTime & " secondes" & return & myLoto)
++++++++++
Bonne journée.
--
Michel Vauquois - <http://michelvauquois.free-h.fr>
Aux armes ! Ne nous laissons pas dupliquer par la parallaxe de l'étranger !
Avatar
josephb
M.V. après avoir mûrement réfléchi nous suggère :
Juste pour le fun...
Script modifié qui permet de choisir le nombre de nombres à
tirer et le nombre de tirages à effectuer :

Ben voilà, sur le sujet (en AppleScript pur et dur) je ne crois pas
qu'on pourra faire beaucoup mieux.
--
J. B.
Pas de panique ! Polariser l'hologramme calorifique ne nous empêche pas
d'améliorer la sustentation érectile ni même de pournifier
l'hepta-impulsion alternative.
Avatar
pdorange
pehache wrote:
Il faudrait vraiment un très gros défaut dans le générateur pour que les
occurrences de chaque nombre devient de l'équiprobabilité. De plus tu
vas forcément trouver des déviations statistiques, qu'il va falloir
analyser pour savoir si elles sont normales ou pas.
Un défaut plus courant et plus difficile à mettre en évidence dans les
générateurs de nombres aléatoire ce sont les séquences prédictibles :
- par exemple 2 est suivi d'un 20, alors le générateur sort plus souvent
un 15 qu'autre chose en suivant.
- ou bien si un nombre quelconque sort au tirage N, alors il a plus de
chances de ressortir qu'un autre au tirage N+P

Comme cela avait était dis dans l'enfilade initiale, c'est en effet le
biais des générateurs pseudo-aléatoire généré par des système numérique
précis.
Un ordinateur n'est guère adapté a généré du vrai aléatoire (par sa
nature préxise).
Et c'est en effet le risque d répétition de séquence qui est a craindre,
pas la répartition globale.
--
Pierre-Alain Dorange Moof <http://clarus.chez-alice.fr/>
Ce message est sous licence Creative Commons "by-nc-sa-2.0"
<http://creativecommons.org/licenses/by-nc-sa/2.0/fr/>
Avatar
pdorange
M.V. wrote:
Mon script : ++++++++++ set myLoto to {} set t0 to (time of (current
date)) --start timer set listeCompt to {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0} repeat 100000 times set tempNb to
random number from 1 to 48 set item tempNb of listeCompt to ((item tempNb
of listeCompt) + 1) end repeat set totalTime to (((time of (current date))
- t0) & " sec") as string --stop timer -- display alert "Temps écoulé : "
& totalTime repeat with j from 1 to 48 set tempResultat to (j & " : " &
item j of listeCompt) as text copy tempResultat to the end of myLoto end
repeat
set text item delimiters to {return} return "Temps écoulé : " & totalTime
& return & myLoto ++++++++++

J'en profite pour proposer un script Python équivalent
import random
nb0000
offset=1
sizeH
result=[0]*size
for t in range(nb):
z=int(size*random.random())
result[z]=result[z]+1
v=offset
for i in result:
print v,i
v=v+1
Qui s'éxécute en moisn d'1 seconde sur un viel iMac de 2008.
--
Pierre-Alain Dorange Moof <http://clarus.chez-alice.fr/>
Ce message est sous licence Creative Commons "by-nc-sa-2.0"
<http://creativecommons.org/licenses/by-nc-sa/2.0/fr/>
Avatar
michel.vauquois
Joseph-B wrote:
Là on entre dans une analyse fine qui dépasse largement le cadre de ce
petit jeu.
De plus il faut avoir la répartition "physique" des nombres dans la
liste, un simple décompte des occurences ne suffit plus. Ça devient du
lourd !

J'ai fait la chose suivante pour des tirages de nombres de 1 à
10.
À chaque tirage, la liste des 10 nombres est "brassée"
aléatoirement et le tirage se fait dans cette liste "brassée" et
non plus simplement par :
++++++++++
set tempNb to random number from 1 to 10
++++++++++
Ceci pour tenter d'éviter ce que PAD a nommé "le risque de
répétition de séquences, pas la répartition globale."
Cf.
<news:1moh0w5.os8s9c4ys2l0N%
J'obtiens par exemple:
Nombre de tirages : 10000
Le nombre 1 a été tiré 989 fois.
Le nombre 2 a été tiré 987 fois.
Le nombre 3 a été tiré 1015 fois.
Le nombre 4 a été tiré 1018 fois.
Le nombre 5 a été tiré 1010 fois.
Le nombre 6 a été tiré 965 fois.
Le nombre 7 a été tiré 1018 fois.
Le nombre 8 a été tiré 997 fois.
Le nombre 9 a été tiré 1053 fois.
Le nombre 10 a été tiré 948 fois.
et pour seulement 1 000 tirages :
Nombre de tirages : 1000
Le nombre 1 a été tiré 106 fois.
Le nombre 2 a été tiré 98 fois.
Le nombre 3 a été tiré 108 fois.
Le nombre 4 a été tiré 98 fois.
Le nombre 5 a été tiré 99 fois.
Le nombre 6 a été tiré 93 fois.
Le nombre 7 a été tiré 84 fois.
Le nombre 8 a été tiré 107 fois.
Le nombre 9 a été tiré 115 fois.
Le nombre 10 a été tiré 92 fois.
Avec la commande simple de tirage aléatoire, j'obtiens :
Nombre de tirages : 1000
Le nombre 1 a été tiré 57 fois.
Le nombre 2 a été tiré 100 fois.
Le nombre 3 a été tiré 86 fois.
Le nombre 4 a été tiré 134 fois.
Le nombre 5 a été tiré 97 fois.
Le nombre 6 a été tiré 133 fois.
Le nombre 7 a été tiré 115 fois.
Le nombre 8 a été tiré 111 fois.
Le nombre 9 a été tiré 108 fois.
Le nombre 10 a été tiré 59 fois.
et c'est systématique : les nombres 1 et 10 sont très peu
tirés...
--
Michel Vauquois
<http://michelvauquois.free-h.fr>
Avatar
josephb
M.V. estime devoir nous faire part de ceci :
et c'est systématique : les nombres 1 et 10 sont très peu
tirés...

De mon côté, j'avais remarqué (comme mentionné par pehache) qu'avec la
fonction "random" de base, un nombre qui vient de sortir a une plus
grande probabilité de ressortir au coup suivant. Même si au long cours
ça n'impacte pas la répartition moyenne, sur des petites séries ça peut
être un biais non négligeable.
Il faut donc augmenter le facteur d'aléa si on veut être un peu plus
rigoureux.
--
J. B.
Voici l'aimant dimensionnel dont il est temps d'améliorer la
multi-turbulence alvéolée sans oublier de pournifier le conduit dirigé.
Avatar
michel.vauquois
Re-bonjour,
Joseph-B, complètement torché, nous apprend :
De mon côté, j'avais remarqué (comme mentionné par pehache) qu'avec la
fonction "random" de base, un nombre qui vient de sortir a une plus
grande probabilité de ressortir au coup suivant. Même si au long cours
ça n'impacte pas la répartition moyenne, sur des petites séries ça peut
être un biais non négligeable.

Apparemment, le nombre de nombres joue également un rôle important.
Toujours avec 10 nombres :
Nombre de tirages : 10000
Le nombre 1 a été tiré 560 fois.
Le nombre 2 a été tiré 1098 fois.
Le nombre 3 a été tiré 1090 fois.
Le nombre 4 a été tiré 1131 fois.
Le nombre 5 a été tiré 1119 fois.
Le nombre 6 a été tiré 1168 fois.
Le nombre 7 a été tiré 1105 fois.
Le nombre 8 a été tiré 1033 fois.
Le nombre 9 a été tiré 1117 fois.
Le nombre 10 a été tiré 579 fois.
On n'avait pas remarqué ces "aberrations" avec 50 nombres... ou alors,
mon script a un bémol !
Amicalement.
--
Michel Vauquois - <http://michelvauquois.free-h.fr>
Faut-il spiro-fracasser le proto-conduit ou bien moribaffer le tunnel ?
Comment savoir !
Avatar
pdorange
M.V. wrote:
Ceci pour tenter d'éviter ce que PAD a nommé "le risque de
répétition de séquences, pas la répartition globale."

Tu ne peux éviter ce biais, qui est inérant aux méthodes
pseudo-aléatoire. Et il n'y a que ce type de méthode qui est accessible
aux ordinateurs.
Leur nature numérique précise, les rend incapable de générer par
eux-même de l'aléatoire.
Les développeurs et mathématiciens penchent sur ces problèmes depuis la
nuit des temps (enfin le début d' l'informatique quoi).
Les solutions mises en ½uvre vont un peu dans le sens que tu testes,
ajouter de la complexité afin de réduire le risque, mais ce n'est qu'un
risque réduit pas une disparition du risque.
Par exemple souvent (c'est le cas en C par exemple) les codes
pseudo-aléatoire permettent de lancer la séquence avec un clé (ou seed)
et on peut chosiir cette clé en se basant sur la date et l'heure. Mais
avec la même clé on obtiendra la même séquence "aléatoire" (sic)...
Pour avoir un véritable aléatoire, il faudrait se baser (comme
référence) sur un évènement aléatoire, par exemple la valeur du champ
magnétique du lieu et au moment de l'utilisation de la fonction, ou
d'autres évènements suffisamment chaotique pour servir de marqueur
aléatoire. Mais ça ne peut qu'être un évènement externe à l'ordinateur
qui lui par construction doit être précis et est justement conçu pour
éviter les évènements interne aléatoire.
A noter que dans la très grand majorité des cas, le pseudo-aléatoire
suffit et heureusement.
--
Pierre-Alain Dorange Moof <http://clarus.chez-alice.fr/>
Ce message est sous licence Creative Commons "by-nc-sa-2.0"
<http://creativecommons.org/licenses/by-nc-sa/2.0/fr/>
Avatar
michel.vauquois
Joseph-B wrote:
Ici, 50 sec pour 1 000 000 tirages

J'ai fait des essais sur mon iMac...
1 seconde (et parfois 0 seconde ! ) pour 10 000 tirages et 52 secondes
pour 1 000 000 tirages sans brassage de la liste de 50 nombres.
En brassant la liste à chaque tirage, 134 secondes pour 10 000 tirages.
Je n'essaierai pas pour 1 000 000 tirages avec brassage de la liste des
nombres !
--
Michel Vauquois
<http://michelvauquois.free-h.fr>
1 2 3 4