Inscrit le: 23 Aoû 2007 Messages: 4766 Sujets: 136 Spécialité en worldedit: Keskesapeutfout' Médailles: 1 (En savoir plus...)
Posté le: 30/08/08 16:25 Sujet du message: Les secrets des Memory Leaks
Dans ce tuto je vais faire de mon mieux pour vous expliquer ce qu'est le memory leak (ou fuite de mémoire en français), comment le "combattre", comment éviter les pièges, et enfin comment vérifier si vous n'avez pas oublié un petit leak par-ci par-là
I/ Le Leak, s'quoi ça ?
a) La véritable identité du leak
Le leak, c'est une information créée par notre ordinateur (enfin plus précisément par Warcraft ) qui ne sera pas supprimée par la suite. Un leak c'est infime, quelques misérables octets. Par rapport à la mémoire vive des ordinateurs, c'est ridicule, un microbe, une infime petite partie qui ne vaut même pas la peine d'être citée.
Maintenant les leaks c'est différent, les leaks : c'est énorme, ce sont des quantités énormes d'informations qui se stockent au fur et à mesure et qui prennent de la place, de la place et toujours plus de place.
A la fin, après toutes ces accumulations, la place prise par ces informations sera plus ou moins énorme selon les fuites.
b) Le leak : le pire ennemi du mappeur (oopa)
Oui enfin c'est bien de savoir tout ça, mais en fait ça change quoi que ça prenne de la place ?
Et bien là est le problème. Les informations stockées sur l'ordinateur vont prendre tellement de place à un certain moment que votre ordinateur va commencer par ramer, puis dans le pire des cas par fatal error Warcraft ou quelque chose dans le genre (manque de mémoire virtuelle, etc...).
Également, lorsque vous quitterez la partie, votre ordinateur mettra plus ou moins de temps selon la puissance de l'ordinateur à revenir au menu principal. N'étant pas pro dans ce domaine, je vais juste me contenter d'émettre l'hypothèse que cela doit être l'ordinateur qui supprime toutes les valeurs stockées, et que ça prend du temps. Bien entendu ça reste une hypothèse, mais de toute façon là n'est pas le problème, le leak saylemal un point c'est tout
II/ Mais d'où vient le leak ???
Le leak est présent sous plusieurs formes. On le trouve dans la création de points, d'effets spéciaux, de groupe d'unités, de textes flottants, et peut-être d'autres.
Ce qui veut dire que chaque fois que vous allez créer une de ces informations, elle sera stockée en mémoire à tout jamais... Enfin sauf si vous la supprimez
Un petit exemple d'un leak :
Secret:
Gui:
Trigger:
Cheat
Evénements
Joueur - Joueur 1 (Rouge) types a chat message containing Je suis un tricheur as Résultat équivalent
Conditions
Actions
Unité - Create 1 Infernal for Joueur 1 (Rouge) at (Center of (Playable map area)) facing Orientation bâtiment par défaut degrees Effet spécial - Create a special effect at (Center of (Playable map area)) using AbilitiesSpellsHumanThunderClapThunderClapCaster.mdl
Ici nous avons 3 leaks :
Le (Center of (Playable map area)) dans la première action ;
Le (Center of (Playable map area)) dans la deuxième action ;
L'effet spécial de la deuxième action qui n'est pas détruit.
Ces leaks ne sont pas très graves dans la mesure où la commande n'est pas utilisée très souvent dans la partie (à moins d'être un ultra imba cheater ).
Mais c'est à ça que vous devrez faire attention
III/ Identification précise des leaks
a) Les points
Comme vu précédemment, les points sont sources de leaks, et sûrement les plus courantes. Un exemple a été vu plus haut.
b) Les groupes d'unité
Probablement la deuxième cause de leak, les groupes d'unités sont également créateurs de leaks. Un petit exemple d'un déclencheur qui produit du leak :
Secret:
Gui:
Trigger:
Volcan
Evénements
Temps - Every 0.50 seconds of game time
Conditions
Actions
Groupe unité - Pick every unit in (Units in VOLCAN <gen>) and do (Actions)
Boucle - Actions
Unité - Set life of (Picked unit) to ((Vie of (Picked unit)) - 10.00)
c) Les effets spéciaux
Ils sont aussi couramment utilisés et tout aussi dangereux, un exemple de ce qu'il ne faut pas faire :
Secret:
Gui:
Trigger:
Explosion
Evénements
Temps - Every 2.00 seconds of game time
Conditions
Actions
Effet spécial - Create a special effect attached to the origin of Paladin 0000 <gen> using AbilitiesSpellsHumanThunderClapThunderClapCaster.mdl
d) Les textes flottants
Si ils ne sont pas supprimés ils peuvent également être sources de leaks.
Secret:
Gui:
Trigger:
Mouration de Hero
Evénements
Unité - A unit Meurt
Conditions
((Dying unit) is Un héros) Egal à TRUE
Actions
Texte flottant - Create floating text that reads BOUH LE GROS NOOB ! above (Dying unit) with Z offset 0.00, using font size 10.00, color (100.00%, 100.00%, 100.00%), and 0.00% transparency
e) Les régions
Un peu moins courantes, les régions peuvent tout de même poser des problèmes.
IV/ La solution
Oui je vous en ai dit pleins jusque là, mais pas comment résoudre ce problème. Enfin si en fait je vous l'ai dit : il faut supprimer l'information stockée. Nous allons voir comment...
a) Les points
Tout d'abord il faudra que vous passiez par une variable. Souvent on appelle cette variable TmpPoint, Tmp pour Temporaire, car le point sera supprimé immédiatement après son utilisation. Il faudra donc créer une variable nommée TmpPoint, bien sûr de type point.
Pour supprimer un point, il faut utiliser cette action (en Jass) :
Bien entendu le TmpPoint sera remplacé par le nom de la variable que vous utilisez.
Pourquoi udg_ ? Car la variable que nous utilisons est une variable globale (pour savoir ce qu'est une variable locale, je vous recommande ce tuto : Variables locales en GUI). Vous ne devrez donc pas enlever le udg_, à moins d'utiliser une variable locale.
Voici donc comment procéder :
Secret:
Gui:
Trigger:
Evénements
Joueur - Joueur 1 (Rouge) types a chat message containing Je suis un tricheur as Résultat équivalent
Conditions
Actions
Set TmpPoint = (Center of (Playable map area)) Unité - Create 1 Infernal for Joueur 1 (Rouge) at TmpPoint facing Orientation bâtiment par défaut degrees Custom script: call RemoveLocation( udg_TmpPoint )
Là nous supprimons la point juste après son utilisation, donc il ne prend pas de mémoire sur le temps.
/!\ Il faut bien penser à mettre la variable dans l'action qui utilise le point. Si vous mettez l'exemple qui suit, votre variable n'aura servi à rien , et il y aura donc du leak :
Gui:
Trigger:
Unité - Create 1 Infernal for Joueur 1 (Rouge) at (Center of (Playable map area)) facing Orientation bâtiment par défaut degrees
b) Les groupes d'unités
Pour supprimer les groupes d'unités, nous allons procéder de la même façon qu'avec les points. Vous devrez donc créer une variable nommée TmpGroup de type Groupe unité.
L'action à utiliser pour supprimer un groupe est la suivante :
Gui:
Trigger:
Custom script: call DestroyGroup( udg_TmpGroup )
Toujours pareil, adaptez le nom de votre variable si vous n'utilisez pas le même nom.
Voici donc notre exemple de tout à l'heure qui ne leak plus :
Secret:
Gui:
Trigger:
Volcan
Evénements
Temps - Every 0.50 seconds of game time
Conditions
Actions
Set TmpGroup = (Units in VOLCAN <gen>)
Groupe unité - Pick every unit in TmpGroup and do (Actions)
Boucle - Actions
Unité - Set life of (Picked unit) to ((Vie of (Picked unit)) - 10.00)
Custom script: call DestroyGroup( udg_TmpGroup )
/!\ Il faut bien penser à mettre la variable dans l'action qui utilise le groupe.
Il faut aussi savoir qu'il existe une autre méthode pour éviter qu'un groupe leak. Même si cette méthode semble être aussi efficace que le première, je préfère vous dire que je ne l'utilise pas. Bien entendu vous faites ce que vous voulez
Cette méthode consiste à mettre l'action suivante juste avant la création du leak :
Gui:
Trigger:
Custom script: set bj_wantDestroyGroup = true
Voici donc notre exemple fait avec la méthode 2 :
Secret:
Gui:
Trigger:
Volcan
Evénements
Temps - Every 0.50 seconds of game time
Conditions
Actions
Custom script: set bj_wantDestroyGroup = true
Groupe unité - Pick every unit in (Units in VOLCAN <gen>) and do (Actions)
Boucle - Actions
Unité - Set life of (Picked unit) to ((Vie of (Picked unit)) - 10.00)
c) Les effets spéciaux
Alors là ça va devenir un peu plus délicat...
Comme vous le savez sûrement déjà, un effet spécial ne fait son animation le plus souvent qu'une seule fois. Dans ce cas là, vous aurez juste à détruire l'effet spécial juste après sa création, on verra quand même l'animation. Exemple :
Secret:
Gui:
Trigger:
Explosion
Evénements
Temps - Every 2.00 seconds of game time
Conditions
Actions
Effet spécial - Create a special effect attached to the origin of Paladin 0000 <gen> using AbilitiesSpellsHumanThunderClapThunderClapCaster.mdl Effet spécial - Destroy (Last created special effect)
On détruit l'effet juste après sa création, mais on le voit quand même.
Maintenant si on veut utiliser un effet qui dure sur la durée, on va être bloqué car si on le supprime tout de suite après sa création, on n'aura même pas le temps de le voir.
La solution dans ce cas là est l'utilisation des variables locales.
Si vous ne connaissez pas, je vous recommande ce tuto : Variables locales en GUI.
Commencez donc par créer une variable de type effet spécial nommée TmpEffect.
Voilà comment nous allons procéder :
Secret:
Gui:
Trigger:
Quete
Evénements
Joueur - Joueur 1 (Rouge) Sélectionne a unit
Conditions
Actions
Custom script: local effect udg_TmpEffect = null -------- TOUJOURS mettre les local en tout début de déclencheur -------- -------- On crée l'effet... -------- Effet spécial - Create a special effect attached to the overhead of (Triggering unit) using AbilitiesSpellsOtherTalkToMeTalkToMe.mdl -------- Puis on le met dans notre variable... -------- Set TmpEffect = (Last created special effect) -------- On attend... -------- Wait 5.00 seconds -------- Puis on détruit notre effet, resté dans notre variable -------- Effet spécial - Destroy TmpEffect
Pourquoi devons-nous utiliser une variable locale ?
Normalement en suivant le tuto d'Ayane vous aurez compris.
Si jamais le déclencheur se déclenche deux fois de suite, seulement un des effets sera supprimé.
Voici par exemple ce qui se passerait si nous n'avions pas mis la variable en locale :
Je sélectionne une unité (un effet est créé)
On attend 2 secondes
On sélectionne une autre unité (la variable prend alors en mémoire le dernier effet créé, et oublie le tout premier effet créé)
On attend 5 secondes
Le deuxième effet sera supprimé, mais pas le tout premier, donc leak.
J'espère que vous aurez compris avec ça
d) Les textes flottants
On fonctionnera de la même façon que les effets en local :
Secret:
Gui:
Trigger:
Mouration de Hero
Evénements
Unité - A unit Meurt
Conditions
((Dying unit) is Un héros) Egal à TRUE
Actions
Custom script: local texttag udg_TmpText = null -------- TOUJOURS mettre les local en tout début de déclencheur -------- -------- On crée le texte... -------- Texte flottant - Create floating text that reads BOUH LE GROS NOOB ! above (Dying unit) with Z offset 0.00, using font size 10.00, color (100.00%, 100.00%, 100.00%), and 0.00% transparency -------- Puis on le met dans notre variable... -------- Set TmpText = (Last created floating text) -------- On attend... -------- Wait 5.00 seconds -------- Puis on détruit notre texte, resté dans notre variable -------- Texte flottant - Destroy (Last created floating text)
Bon je vais faire un déclencheur qui pourrait créer un gros leak, à vous de le corriger :
Secret:
Gui:
Trigger:
Declencheur ultra super mega over imba complique
Evénements
Temps - Every 0.50 seconds of game time
Conditions
Actions
Effet spécial - Create a special effect at (Center of VOLCAN <gen>) using OMG LA GROSSE EXPLOSION DE SA RACE ! Texte flottant - Create floating text that reads *brûle* at (Random point in VOLCAN <gen>) with Z offset 0.00, using font size 10.00, color (100.00%, 100.00%, 100.00%), and 0.00% transparency
Groupe unité - Pick every unit in (Units in VOLCAN <gen>) and do (Actions)
Boucle - Actions
Unité - Set life of (Picked unit) to ((Vie of (Picked unit)) - 10.00)
Bien entendu je précise que ce déclencheur est d'une grand inutilité, c'est juste pour vous donner un exemple
Alors vous trouvez ?
...
...
...
Toujours pas ???
...
...
...
Bon allez je vous donne la solution
Secret:
Gui:
Trigger:
Declencheur ultra super mega over imba complique
Evénements
Temps - Every 0.50 seconds of game time
Conditions
Actions
Custom script: local texttag udg_TmpText = null Set TmpPoint = (Center of VOLCAN <gen>) Effet spécial - Create a special effect at TmpPoint using OMG LA GROSSE EXPLOSION DE SA RACE ! Custom script: call RemoveLocation( udg_TmpPoint ) Effet spécial - Destroy (Last created special effect) Set TmpPoint = (Random point in VOLCAN <gen>) Texte flottant - Create floating text that reads *brûle* at TmpPoint with Z offset 0.00, using font size 10.00, color (100.00%, 100.00%, 100.00%), and 0.00% transparency Custom script: call RemoveLocation( udg_TmpPoint ) Set TmpText = (Last created floating text) Set TmpGroup = (Units in VOLCAN <gen>)
Groupe unité - Pick every unit in TmpGroup and do (Actions)
Boucle - Actions
Unité - Set life of (Picked unit) to ((Vie of (Picked unit)) - 10.00)
Set TmpPoint = (Center of (Playable map area)) Unité - Create 1 Fantassin for Joueur 1 (Rouge) at (TmpPoint offset by 256.00 towards 0.00 degrees) facing Orientation bâtiment par défaut degrees Custom script: call RemoveLocation( udg_TmpPoint )
Ce n'est pas bon ! On a deux points ici ! Un qui est supprimé, pas le deuxième. Voilà comment procéder :
Secret:
Gui:
Trigger:
Actions
Set TmpPoint[1] = (Center of (Playable map area)) Set TmpPoint[2] = (TmpPoint[1] offset by 256.00 towards 0.00 degrees) Unité - Create 1 Fantassin for Joueur 1 (Rouge) at TmpPoint[2] facing Orientation bâtiment par défaut degrees Custom script: call RemoveLocation( udg_TmpPoint[2] ) Custom script: call RemoveLocation( udg_TmpPoint[1] )
VI/ Un petit logiciel bonus
Vous avez de la chance j'ai réussi à me rappeller comment il s'appelait et je l'ai retrouvé
LeakCheck vous permet de vérifier s'il reste du leak dans votre déclencheur.
Me semble que pour l'effet spécial bryce avait préciser que l'on pouvait directement supprimer l'effet et qu'il se jouerai quand même si non gg et merci pour le logiciel anti leak _________________
Inscrit le: 21 Aoû 2007 Messages: 2073 Sujets: 38 Spécialité en worldedit: Oui Médailles: 1 (En savoir plus...)
Posté le: 30/08/08 16:42 Sujet du message:
Oui l'effet spécial c'est vrai, mais il jouera l'animation death, donc c'est valable uniquement pour les effets comme le sort du MK (roi de la montagne)
Aussi la "2eme méthode" n'est pas parfaite car elle détruit les groupes (Units of Type) avant leur utilisation.
Inscrit le: 23 Aoû 2007 Messages: 7143 Sujets: 147 Spécialité en worldedit: le troll, le flood, la vulgarité, mon coeur balance Médailles: 2 (En savoir plus...)
Posté le: 30/08/08 16:52 Sujet du message:
Pour les texte flottant pas besoin de variable, si son temps est défini, l'action gui pour définir le temps d'apparition suffit amplement (je ne me rappelle plus le nom exact).
Qu'as tu contre set bj_wantDestroyGroup=true ? _________________
Inscrit le: 23 Aoû 2007 Messages: 4766 Sujets: 136 Spécialité en worldedit: Keskesapeutfout' Médailles: 1 (En savoir plus...)
Posté le: 30/08/08 17:20 Sujet du message:
General Vans a écrit:
Partie V/ b)
Set TmpPoint[2] = (TmpPoint2[1] offset by 256.00 towards 0.00 degrees)
C'est
Set TmpPoint[2] = (TmpPoint[1] offset by 256.00 towards 0.00 degrees)
Mince merci, je voulais éviter de recrée une variable D:
The.gosu a écrit:
Me semble que pour l'effet spécial bryce avait préciser que l'on pouvait directement supprimer l'effet et qu'il se jouerai quand même si non gg et merci pour le logiciel anti leak
Lis tout le tuto.
Keitaro_Ura a écrit:
Oui l'effet spécial c'est vrai, mais il jouera l'animation death, donc c'est valable uniquement pour les effets comme le sort du MK (roi de la montagne)
Aussi la "2eme méthode" n'est pas parfaite car elle détruit les groupes (Units of Type) avant leur utilisation.
Très bon tuto.
Voilà c'est ça.
Ah ? Je savais pas, bah maintenant j'ai une raison valable pour dire que je l'utilise pas ^^
Merci
Troll-Brain a écrit:
Pour les texte flottant pas besoin de variable, si son temps est défini, l'action gui pour définir le temps d'apparition suffit amplement (je ne me rappelle plus le nom exact).
Qu'as tu contre set bj_wantDestroyGroup=true ?
Nan ça leak quand même je crois, j'avais fait des tests. (à vrai dire si je me souvient bien je n'avais pas mis de temps de vie !).
Cf la réponse au dessus _________________
Leçon n°1 du WorldEdit : « Le violet > Troll-Brain »
Inscrit le: 23 Aoû 2007 Messages: 7143 Sujets: 147 Spécialité en worldedit: le troll, le flood, la vulgarité, mon coeur balance Médailles: 2 (En savoir plus...)
Posté le: 30/08/08 18:42 Sujet du message:
Oui et d'ailleurs tu peux le tester facilement.
Et un texte flottant ne leak pas s'il n'est pas permanent et que l'on définit sa durée. _________________
Inscrit le: 22 Nov 2007 Messages: 677 Sujets: 27 Spécialité en worldedit: Jamais sortir ses projets ?
Posté le: 30/08/08 20:58 Sujet du message:
Si tu suit le tuto tu te retrouve avec beaucoup de variable local , alors même minime , si ont l'utilise pas mal dans des périodiques sa peut être aussi important qu'un leak moins fréquents. _________________
Toutes les heures sont au format GMT + 1 Heure Aller à la page 1, 2, 3, 4, 5, 6, 7, 8, 9, 10Suivante
Page 1 sur 10
Vous ne pouvez pas poster de nouveaux sujets dans ce forum Vous ne pouvez pas répondre aux sujets dans ce forum Vous ne pouvez pas éditer vos messages dans ce forum Vous ne pouvez pas supprimer vos messages dans ce forum Vous ne pouvez pas voter dans les sondages de ce forum