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

Nombres aléatoires sans doublons

29 réponses
Avatar
Emile63
Bonjour Í  tous

En ces temps de confinement j'en profite pour répéter un peu mon anglais :-)
en me basant sur un classeur, qui contient une table de mots anglais (col.2 -> français col.1)
Avec une petite procédure, partiellement copiée ci-après, il m'apparait aléatoirement un mot que je dois identifier et traduire.
Le problème c'est que comme cette proc. fonctionne avec un générateur de nombres aléatoires (Randomize) certains mots reviennent plusieurs fois, alors que d'autres jamais... :(
Comment puis-je modifier ça pour que la variable "VocPosition" de donne pas deux fois le même chiffre et les utiles tous ?

'-----------------------------------------------------------------------------------------
Set VocTbl = ThisWorkbook.Worksheets("Liste des mots")
MaxVoc = (VocTbl.Cells(12, 2).End(xlDown).Row) - 10 'Compte le NB de mots de la colonne 2
Do
Randomize ' Initialise le générateur de nombres aléatoires.
VocPosition = Int((MaxVoc * Rnd) + 1) 'choisir un mot aléatoirement
'Bla, bla, Bla.

Loop While NouvelleEntrée = True
'-----------------------------------------------------------------------------------------

Je vous remercie d'avance pour votre aide et dans cette attente vous souhaite une très bonne journée.

10 réponses

1 2 3
Avatar
Emile63
Le Wednesday, December 2, 2020 Í  1:40:33 AM UTC+1, MichD a écrit :
Merci pour ta sollicitude.
J'ai envoyé une image écran, mais je me rends bien compte que ce n'est pas très explicite. :(
Je crois que cette feuille a commencé Í  vivre avec Office 95, et donc les textbox et feuille de dialogue n'étaient pas ce qu'ils sont aujourd'hui, l'idée générale étant de ne pas devoir refaire un nouvel Userform et sauver la feuille de dialogue existante ;)
Du coup je me permet de t'envoyer un fichier exemple:
https://www.cjoint.com/c/JLbqCNl0HjN
Donc depuis l'onglet : "Vocabulaire" il faut cliquer sur le bouton : "Entraͮnement"
Ceci fait apparaÍ®tre une boÍ®te de dialogue avec un mot en français (par défaut) qu'il faut écrire en anglais dans le contrÍ´le "traduction" puis valider avec "Enter" (C'est ça qui ne fonctionne plus)
La procédure compare les deux mots et valide ou invalide le mot écrit en faisant évoluer les résultats.
Puis la boucle recommence jusqu'Í  ce qu'elle ait parcouru l'ensemble de la BDD sans doublons ;)
Un clic sur le bouton "Fin" de la boͮte de dialogue met fin ͠ "l'entraͮnement"
VoilÍ , j'espère que c'est plus clair maintenant.
Merci pour ton aide et bonne fin de journée,
Emile
J'ai pris le temps de regarder la procédure. Le textbox dans la feuille
DLG peut afficher du texte, mais je ne crois pas qu'il soit possible que
ce contrÍ´le réagisse au simple fait d'appuyer sur la touche "Enter".
Cette technologie n'existe pas Í  l'époque! Tu vas devoir ajouter un
bouton et lui affecter une macro qui va faire ce que tu veux.
Personnellement, je te suggère l'utilisation d'un formulaire (userform).
Les possibilités de programmation sont beaucoup plus grandes et plus
flexibles.
MichD

Bonjour MichD,
J'ai suivi ton conseil et me suis lancé Í  passer ma feuille (d'entrainement Í  l'anglais), de l'ancienne version Í  un formulaire userform. ;-)
J'ai donc adapté la procédure précédente au nouvel environnement, mais lÍ  ça fait un moment que je n'avance plus et bute sur un souci. :-(
La procédure est lancée depuis un bouton [EntraÍ®ner] sur la feuille de travail et suit un certain nombre d'étapes qui consistent Í  sélectionner extraire un mot [Français] qui apparaÍ®tra dans un label du formulaire userform et l'utilisateur doit répondre dans un autre label par sa traduction [en anglais], puis la procédure vérifie que les deux mots correspondent Í  ce qui se trouve dans la base de données, et si c'est ok, valide le mot et recommence l'opération jusqu'Í  ce que tous les mots aient été passés en revue ou qu'on mette fin Í  la procédure .
Toute cette étape semble fonctionner jusqu'au moment ou j'ouvre le formulaire:
UserForm1.Show
A partir d'ici , la procédure s'arrête et même si je remplis le label et valide [enter], il ne se passe rien.
L'application Í  créer une proc. événementielle:
Private Sub Label5_Change()
........
End Sub
Mais je ne sais pas trop quoi en faire... J'y ai écris ceci: Réponse = UserForm1.Label5.Text pour récupérer le mot qui est écris dans le label, mais dès la première lettre l'événement se déclenche et la procédure se termine, puis j'ai changé cet événement contre:
Sub Label5_Exit(ByVal Cancel As MSForms.ReturnBoolean)
Réponse = UserForm1.Label5.Text
End Sub
ça fonctionne mieux, mon mot est gardé dans la variable: "Réponse", mais je ne sais pas comment retourner ce "mot" Í  ma procédure initiale qui attend le mot pour la comparaison.
VoilÍ , je ne sais pas si tu me comprendras, mais j'espère avoir correctement décris le problème sans mettre ici des kilomètre de procédure...
Merci d'avance pour ta compréhension, dans l'espoir d'avoir quelques piste pour me sortir de cette impasse je te souhaite un très bon week-end.
Cordialement
Avatar
MichD
Le 03/04/21 Í  04:07, Emile63 a écrit :
Bonjour,
'------------------
mon mot est gardé dans la variable: "Réponse", mais je ne sais pas
comment retourner ce "mot" Í  ma procédure initiale qui attend le mot
pour la comparaison
'------------------
Il est très difficile de te donner une réponse sans rien voir!
A ) Si tu définis la variable "Réponse", cette dernière est disponible
dans d'autres procédures si besoin.
B ) Lorsque l'événement Sub Label5_Exit(ByVal Cancel As
MSForms.ReturnBoolean) s'exécute, tu peux appeler une procédure en
utilisant cette variable en paramètre(si tu fais cela, tu définis la
variable "Réponse" au niveau de la procédure et non dans le haut du module)
'---------------------------------
Sub Label5_Exit(ByVal Cancel As MSForms.ReturnBoolean)
dim réponse As String
Réponse = Userform1.Label5.text
Call MaProcésure(Réponse)
End Sub
'--------------------------------
"MaProcédure" est un bout de macro qui complète le travail Í  exécuter.
'----------------------------------
Sub MaProcédure(MaVar As String)
'Le code qui permet de faire la comparaison
End Sub
'------------------------------------
MichD
Avatar
Emile63
Le Saturday, April 3, 2021 Í  4:29:39 PM UTC+2, MichD a écrit :
Le 03/04/21 Í  04:07, Emile63 a écrit :
Bonjour,
'------------------
mon mot est gardé dans la variable: "Réponse", mais je ne sais pas
comment retourner ce "mot" Í  ma procédure initiale qui attend le mot
pour la comparaison
'------------------
Il est très difficile de te donner une réponse sans rien voir!
A ) Si tu définis la variable "Réponse", cette dernière est disponible
dans d'autres procédures si besoin.
B ) Lorsque l'événement Sub Label5_Exit(ByVal Cancel As
MSForms.ReturnBoolean) s'exécute, tu peux appeler une procédure en
utilisant cette variable en paramètre(si tu fais cela, tu définis la
variable "Réponse" au niveau de la procédure et non dans le haut du module)
'---------------------------------
Sub Label5_Exit(ByVal Cancel As MSForms.ReturnBoolean)
dim réponse As String
Réponse = Userform1.Label5.text
Call MaProcésure(Réponse)
End Sub
'--------------------------------
"MaProcédure" est un bout de macro qui complète le travail Í  exécuter.
'----------------------------------
Sub MaProcédure(MaVar As String)
'Le code qui permet de faire la comparaison
End Sub
'------------------------------------
MichD

Bonjour MichD,
Je comprend bien que sans rien voir, ça parait un peu compliqué..
Je me permets une version allégée ici: https://www.cjoint.com/c/KDdpRvt3qpN
Merci de ton aide
Bon après-midi
Avatar
Emile63
Le Saturday, April 3, 2021 Í  5:46:07 PM UTC+2, Emile63 a écrit :
Le Saturday, April 3, 2021 Í  4:29:39 PM UTC+2, MichD a écrit :
Le 03/04/21 Í  04:07, Emile63 a écrit :
Bonjour,
'------------------
mon mot est gardé dans la variable: "Réponse", mais je ne sais pas
comment retourner ce "mot" Í  ma procédure initiale qui attend le mot
pour la comparaison
'------------------
Il est très difficile de te donner une réponse sans rien voir!
A ) Si tu définis la variable "Réponse", cette dernière est disponible
dans d'autres procédures si besoin.
B ) Lorsque l'événement Sub Label5_Exit(ByVal Cancel As
MSForms.ReturnBoolean) s'exécute, tu peux appeler une procédure en
utilisant cette variable en paramètre(si tu fais cela, tu définis la
variable "Réponse" au niveau de la procédure et non dans le haut du module)
'---------------------------------
Sub Label5_Exit(ByVal Cancel As MSForms.ReturnBoolean)
dim réponse As String
Réponse = Userform1.Label5.text
Call MaProcésure(Réponse)
End Sub
'--------------------------------
"MaProcédure" est un bout de macro qui complète le travail Í  exécuter.
'----------------------------------
Sub MaProcédure(MaVar As String)
'Le code qui permet de faire la comparaison
End Sub
'------------------------------------
MichD
Bonjour MichD,
Je comprend bien que sans rien voir, ça parait un peu compliqué..
Je me permets une version allégée ici: https://www.cjoint.com/c/KDdpRvt3qpN
Merci de ton aide
Bon après-midi

NB:
En partant sur la base de ton exemple, je perd la boucle :
Do
Randomise et ce qui suit...
Avatar
MichD
ton fichier : https://www.cjoint.com/c/KDdwfI4ZeQj
Ton problème particulier est résolu!
A ) Il faut éviter d'utiliser le truc goto ... ça complique drÍ´lement le
code surtout pour ceux qui doivent y travailler par la suite.
B ) il est préférable de créer des procédures courtes que l'on peut
appeler en utilisant des paramètres Í  ces sub au besoin au lieu d'une
seule longue procédure.
C ) Attention Í  la déclaration des variables. On doit déclarer toutes et
au bon endroit.
Tu as beaucoup de plaisir devant toi. Amuse-toi bien.
MichD
Avatar
MichD
Le 03/04/21 Í  18:11, MichD a écrit :
ton fichier : https://www.cjoint.com/c/KDdwfI4ZeQj
Ton problème particulier est résolu!
A ) Il faut éviter d'utiliser le truc goto ... ça complique drÍ´lement le
code surtout pour ceux qui doivent y travailler par la suite.
B ) il est préférable de créer des procédures courtes que l'on peut
appeler en utilisant des paramètres Í  ces sub au besoin au lieu d'une
seule longue procédure.
C ) Attention Í  la déclaration des variables. On doit déclarer toutes et
au bon endroit.
Tu as beaucoup de plaisir devant toi. Amuse-toi bien.
MichD

Version plus complète : https://www.cjoint.com/c/KDeaxBgTYjj
MichD
Avatar
MichD
Une dernière correction : https://www.cjoint.com/c/KDeljdVaAlj
MichD
Avatar
Emile63
Le Sunday, April 4, 2021 Í  1:10:03 PM UTC+2, MichD a écrit :
Une dernière correction : https://www.cjoint.com/c/KDeljdVaAlj
MichD

Merci MichD pour ce grand travail.
Je rencontre toutefois des problèmes de "Mémoire insuffisante"  :-(
(J'ai bien relancé Excel, mais l'erreur revient, quand je quitte en fin de cycle..).
Est-ce que tu me recommandes une opération particulière pour gérer ça, ou est-ce que ça pourrait venir du  dic ou une erreur de déclaration de variable?
J'ai modifier au hasard la proc.:
--------------------------------------------------------------
Private Sub CommandButton1_Click()
'Fermer le formulaire
Set Dic = Nothing ' <-- ici, mais ça ne change rien Í  l'erreur de mémoire
Me.Hide
Unload UserForm1
End Sub
------------------------------------------------------------
Mais ce n'est pas mieux..  :(
Très bonne journée,
Emile
Avatar
MichD
Le 05/04/21 Í  04:25, Emile63 a écrit :
Le Sunday, April 4, 2021 Í  1:10:03 PM UTC+2, MichD a écrit :
Une dernière correction : https://www.cjoint.com/c/KDeljdVaAlj
MichD

Merci MichD pour ce grand travail.
Je rencontre toutefois des problèmes de "Mémoire insuffisante"  :-(
(J'ai bien relancé Excel, mais l'erreur revient, quand je quitte en fin de cycle..).
Est-ce que tu me recommandes une opération particulière pour gérer ça, ou est-ce que ça pourrait venir du  dic ou une erreur de déclaration de variable?
J'ai modifier au hasard la proc.:
--------------------------------------------------------------
Private Sub CommandButton1_Click()
'Fermer le formulaire
Set Dic = Nothing ' <-- ici, mais ça ne change rien Í  l'erreur de mémoire
Me.Hide
Unload UserForm1
End Sub
------------------------------------------------------------
Mais ce n'est pas mieux..  :(
Très bonne journée,
Emile

Si le problème de "Mémoire insuffisante" provient de l'objet
"Dictionary", j'ai modifié le code et le problème devrait être résolu!
https://www.cjoint.com/c/KDfj6jj0cEj
Tu as noté sÍ»rement lorsque l'on fait la saisie de la traduction d'un
mot, on n'est pas obligé d'entrer le mot complet pour obtenir le message
d'une bonne réponse...Est-ce que c'est par design ou par un manque au
niveau de la programmation?
J'avais testé la dernière version publiée avec une trentaine de mots et
je n'avais pas eu le message de "mémoire insuffisante". Le bouton
"Fermer" du formulaire faisait bien le travail.
MichD
Avatar
MichD
Essaie plutÍ´t cette version : https://www.cjoint.com/c/KDflqO74CHj
MichD
1 2 3