OVH Cloud OVH Cloud

Variable inutilisée

13 réponses
Avatar
Faust
bonjour,

savez-vous s'il existe une procédure qui soit appelée lorsque que le
compteur de référence d'une instance de classe tombe à zéro (donc à
priori quand l'instance n'est plus utilisée où que ce soit et qu'elle
sera libérée par le GC)?

le but étant de permettre à la classe de faire une action particulière
lorsqu'elle détecte qu'on aura plus besoin d'elle (libération de
certaines ressources) sans que le programmeur qui utilise cette classe
soit obligé de faire lui même une gestion fastidieuse pour savoir s'il
peut faire un dispose

à moins (et c'est possible parce que j'ai pas tout compris) que le
paramètre Disposing du Dispose serve justement à ça: que le dispose est
appelé systématiquement à chaque fois qu'une variable passe "out of
scope" avec le paramètre Disposing à false tant qu'il reste des
variables "not out of scope" et passé à true dans le cas où c'est la
dernière variable qui passe "out of scope"?

--
*/Teträm/*
http://www.tetram.info

"Après ton vomi, ne remange pas tout, laisses-en pour tes mouches" -
Proverbe Troll

10 réponses

1 2
Avatar
Paul Bacelar
Contrairement à COM, il n'y pas de compteur de référence en .NET mais un
garbage collector qui permet de ne plus avoir de référence cyclique, entre
autres.

Rien ne vous empêche, grâce à une conception soignée de votre classes et de
ces méthodes d'implémenter votre propre compteur de référence qui appellera
la fonction Dispose quand le compteur atteindra 0.

Le mot clé using permet de simplifier grandement l'utilisation de Dispose

<CODE>

using(titi){

...

}

</CODE>

A la sortie de accolade, la méthode Dispode de titi sera automatiquement
exécuté.

Le paramètre disposing de la méthode Dispose généré par le Designer de
formulaire de VS permet de distinguer entre les deux contextes dans
laquelle cette fonction est appelée.

Avec disposing à true, cela exprime le fait que la méthode Dispose avec un
paramètre bool est appelée à partir de la méthode Dispose de l'interface
IDisposable qui, elle, ne prend pas de paramètre.

Avec disposing à false, cela exprime que la méthode Dispose avec un
paramètre bool est appelée à partir de la méthode Finalize (destructeur non
déterministe de la CLR).

Le code doit connaître le contexte d'appel car dans le Finalize, il n'est
pas garanti que les références contenues par l'objet soient encore valides.



En résumé, il est très simple d'implémenter un compteur de référence adapté
à votre utilisation de la classe d'objet et "using" permet de régler les cas
les plus triviaux.
--
Paul Bacelar


"Faust" wrote in message
news:
bonjour,

savez-vous s'il existe une procédure qui soit appelée lorsque que le
compteur de référence d'une instance de classe tombe à zéro (donc à
priori quand l'instance n'est plus utilisée où que ce soit et qu'elle
sera libérée par le GC)?

le but étant de permettre à la classe de faire une action particulière
lorsqu'elle détecte qu'on aura plus besoin d'elle (libération de
certaines ressources) sans que le programmeur qui utilise cette classe
soit obligé de faire lui même une gestion fastidieuse pour savoir s'il
peut faire un dispose

à moins (et c'est possible parce que j'ai pas tout compris) que le
paramètre Disposing du Dispose serve justement à ça: que le dispose est
appelé systématiquement à chaque fois qu'une variable passe "out of
scope" avec le paramètre Disposing à false tant qu'il reste des
variables "not out of scope" et passé à true dans le cas où c'est la
dernière variable qui passe "out of scope"?

--
*/Teträm/*
http://www.tetram.info

"Après ton vomi, ne remange pas tout, laisses-en pour tes mouches" -
Proverbe Troll



Avatar
Faust
/_Paul Bacelar_ a utilisé son clavier pour écrire/ :
Contrairement à COM, il n'y pas de compteur de référence en .NET mais un
garbage collector qui permet de ne plus avoir de référence cyclique, entre
autres.

Rien ne vous empêche, grâce à une conception soignée de votre classes et de
ces méthodes d'implémenter votre propre compteur de référence qui appellera
la fonction Dispose quand le compteur atteindra 0.

Le mot clé using permet de simplifier grandement l'utilisation de Dispose

<CODE>

using(titi){

...

}

</CODE>

A la sortie de accolade, la méthode Dispode de titi sera automatiquement
exécuté.



le problème de using, c'est qu'il se limite à un contexte court de
code:

using(machin){
// traitement ponctuel
}

or, il se peut que la classe dont je parle soit utilisée dans une autre
classe... et donc son instance aura (au maximum) la même durée de vie
que l'instance de la classe qui la contient

public class bidule
{
machin _machin;
}

or c'est surtout dans ce cas là qu'il m'interresse de savoir quand
l'instance n'est plus accessible

pour le compteur de référence, je vois pas comment je peux faire....
autant à la création de l'instance y'a pas de problème, autant quand je
"partage" l'instance entre plusieurs variables, je n'ai aucune
procédure d'appelée pour incrémenter (ou décrémenter) ce compteur

suis je donc condamné à imposer à l'utilisateur de ma classe, un truc
façon:

_bidule.machin = autrevariablemachin;
_bidule.machin._AddRef(); ?

Le paramètre disposing de la méthode Dispose généré par le Designer de
formulaire de VS permet de distinguer entre les deux contextes dans
laquelle cette fonction est appelée.

Avec disposing à true, cela exprime le fait que la méthode Dispose avec un
paramètre bool est appelée à partir de la méthode Dispose de l'interface
IDisposable qui, elle, ne prend pas de paramètre.

Avec disposing à false, cela exprime que la méthode Dispose avec un
paramètre bool est appelée à partir de la méthode Finalize (destructeur non
déterministe de la CLR).

Le code doit connaître le contexte d'appel car dans le Finalize, il n'est
pas garanti que les références contenues par l'objet soient encore valides.

En résumé, il est très simple d'implémenter un compteur de référence adapté
à votre utilisation de la classe d'objet et "using" permet de régler les cas
les plus triviaux.



merci pour ces infos

--
Mephitiquement votre,
Faust
ICQ #161252577
Avatar
Frédéric Queudret [MS]
Bonjour,

Est-ce que le IDisposable Pattern avec surcharge du Finalizer pourrait
répondre à votre besoin?
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpgenref/html/cpconFinalizeDispose.asp
Il appelle automatiquement Dispose dans le cas de la surcharge du Finalizer
en tenant compte du contexte de l'appel (Dispose ou Finalizer).
cdlt,
Frédéric.
"Faust" wrote in message
news:
bonjour,

savez-vous s'il existe une procédure qui soit appelée lorsque que le
compteur de référence d'une instance de classe tombe à zéro (donc à priori
quand l'instance n'est plus utilisée où que ce soit et qu'elle sera
libérée par le GC)?

le but étant de permettre à la classe de faire une action particulière
lorsqu'elle détecte qu'on aura plus besoin d'elle (libération de certaines
ressources) sans que le programmeur qui utilise cette classe soit obligé
de faire lui même une gestion fastidieuse pour savoir s'il peut faire un
dispose

à moins (et c'est possible parce que j'ai pas tout compris) que le
paramètre Disposing du Dispose serve justement à ça: que le dispose est
appelé systématiquement à chaque fois qu'une variable passe "out of scope"
avec le paramètre Disposing à false tant qu'il reste des variables "not
out of scope" et passé à true dans le cas où c'est la dernière variable
qui passe "out of scope"?

--
*/Teträm/*
http://www.tetram.info

"Après ton vomi, ne remange pas tout, laisses-en pour tes mouches" -
Proverbe Troll



Avatar
Faust
ça semble effectivement plus ou moins être ça, mais certains points
restent obscurs pour moi.

De ce que j'ai compris de ce document:
- le Finalize (destructeur) est appelé par le GC quand celui-ci "fait
du ménage" (qui appelera automatiquement Dispose au besoin)
- la méthode Dispose (ou toute autre méthode appelant la méthode
Dispose, par ex. Close) sera à appeler par l'utilisateur s'il a besoin
de libérer les ressources avant que le GC n'intervienne

en gros, la libération des ressources est explicitement demandée par
l'utlisateur et implicitement demandée par le GC.

ai-je bien compris?

si c'est bien ça, n'y a-t-il vraiement aucun moyen libérer
implicitement (j'insiste sur cette notion) les ressources bien avant
l'intervention du GC?

/Dans son message précédent, _Frédéric Queudret [MS]_ a écrit/ :
Bonjour,

Est-ce que le IDisposable Pattern avec surcharge du Finalizer pourrait
répondre à votre besoin?
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpgenref/html/cpconFinalizeDispose.asp
Il appelle automatiquement Dispose dans le cas de la surcharge du Finalizer
en tenant compte du contexte de l'appel (Dispose ou Finalizer).
cdlt,
Frédéric.
"Faust" wrote in message
news:
bonjour,

savez-vous s'il existe une procédure qui soit appelée lorsque que le
compteur de référence d'une instance de classe tombe à zéro (donc à priori
quand l'instance n'est plus utilisée où que ce soit et qu'elle sera libérée
par le GC)?

le but étant de permettre à la classe de faire une action particulière
lorsqu'elle détecte qu'on aura plus besoin d'elle (libération de certaines
ressources) sans que le programmeur qui utilise cette classe soit obligé de
faire lui même une gestion fastidieuse pour savoir s'il peut faire un
dispose

à moins (et c'est possible parce que j'ai pas tout compris) que le
paramètre Disposing du Dispose serve justement à ça: que le dispose est
appelé systématiquement à chaque fois qu'une variable passe "out of scope"
avec le paramètre Disposing à false tant qu'il reste des variables "not out
of scope" et passé à true dans le cas où c'est la dernière variable qui
passe "out of scope"?

-- */Teträm/*
http://www.tetram.info

"Après ton vomi, ne remange pas tout, laisses-en pour tes mouches" -
Proverbe Troll






--
Mephitiquement votre,
Faust
ICQ #161252577
Avatar
Simon Mourier [MS]
Que cherchez vous à faire au juste? La phrase "le but étant de permettre à
la classe de faire une action particulière lorsqu'elle détecte qu'on aura
plus besoin d'elle" est particulièrement bizarre. Ce n'est pas à la classe
de détecter qu'on n'a plus besoin d'elle en général. Comment peut-elle
mourir si elle doit détecter des choses...
Simon.

"Faust" a écrit dans le message de news:

bonjour,

savez-vous s'il existe une procédure qui soit appelée lorsque que le
compteur de référence d'une instance de classe tombe à zéro (donc à priori
quand l'instance n'est plus utilisée où que ce soit et qu'elle sera
libérée par le GC)?

le but étant de permettre à la classe de faire une action particulière
lorsqu'elle détecte qu'on aura plus besoin d'elle (libération de certaines
ressources) sans que le programmeur qui utilise cette classe soit obligé
de faire lui même une gestion fastidieuse pour savoir s'il peut faire un
dispose

à moins (et c'est possible parce que j'ai pas tout compris) que le
paramètre Disposing du Dispose serve justement à ça: que le dispose est
appelé systématiquement à chaque fois qu'une variable passe "out of scope"
avec le paramètre Disposing à false tant qu'il reste des variables "not
out of scope" et passé à true dans le cas où c'est la dernière variable
qui passe "out of scope"?

--
*/Teträm/*
http://www.tetram.info

"Après ton vomi, ne remange pas tout, laisses-en pour tes mouches" -
Proverbe Troll



Avatar
Faust
mon but n'est pas forcément qu'elle meure... que tous mes pointeurs
restent "vivants" ne me gène pas.
Par contre, j'ai impérativement besoin qu'elle libère certaines
ressources (des connections entre autre)
et pour cela, j'aurais aimé que la classe libère ces différentes
ressources d'elle même.... même si le programmeur "oublie" de faire un
Close, un Dipose ou toute autre action prévue (un peu ceinture et
bretelle)
et donc bien sûr, elle ne doit le faire qu'une fois le programme ne
peut plus la manipuler. En COM ça reviendrait à dire quand le compteur
de référence tombe à 0.

le soucis est que, pour le cas des connections, si elles ne sont pas
libérées correctement ça me pose des problèmes côté serveur

/_Simon Mourier [MS]_ a utilisé son clavier pour écrire/ :
Que cherchez vous à faire au juste? La phrase "le but étant de permettre à la
classe de faire une action particulière lorsqu'elle détecte qu'on aura plus
besoin d'elle" est particulièrement bizarre. Ce n'est pas à la classe de
détecter qu'on n'a plus besoin d'elle en général. Comment peut-elle mourir si
elle doit détecter des choses...
Simon.

"Faust" a écrit dans le message de news:

bonjour,

savez-vous s'il existe une procédure qui soit appelée lorsque que le
compteur de référence d'une instance de classe tombe à zéro (donc à priori
quand l'instance n'est plus utilisée où que ce soit et qu'elle sera libérée
par le GC)?

le but étant de permettre à la classe de faire une action particulière
lorsqu'elle détecte qu'on aura plus besoin d'elle (libération de certaines
ressources) sans que le programmeur qui utilise cette classe soit obligé de
faire lui même une gestion fastidieuse pour savoir s'il peut faire un
dispose

à moins (et c'est possible parce que j'ai pas tout compris) que le
paramètre Disposing du Dispose serve justement à ça: que le dispose est
appelé systématiquement à chaque fois qu'une variable passe "out of scope"
avec le paramètre Disposing à false tant qu'il reste des variables "not out
of scope" et passé à true dans le cas où c'est la dernière variable qui
passe "out of scope"?

-- */Teträm/*
http://www.tetram.info

"Après ton vomi, ne remange pas tout, laisses-en pour tes mouches" -
Proverbe Troll






--
*/Teträm/*
http://www.tetram.info

"Mange d'abord, defeque ensuite: tu réfléchiras plus tard" - Proverbe
Troll
Avatar
Simon Mourier [MS]
Pour les ressources non managées (handles, connexions, etc...) , il faut
utiliser le pattern proposé par IDisposable. C'est en gros l'unique
solution, et c'est comme ca que sont gérées d'ailleurs toutes les ressources
non managées dans le .NET Framework.

Même si le programmeur oublie d'appeler classe.Dispose(), ce sera appelé
automatiquement.

Je ne vois pas ce qui vous manque?
Simon.

"Faust" a écrit dans le message de news:

mon but n'est pas forcément qu'elle meure... que tous mes pointeurs
restent "vivants" ne me gène pas.
Par contre, j'ai impérativement besoin qu'elle libère certaines ressources
(des connections entre autre)
et pour cela, j'aurais aimé que la classe libère ces différentes
ressources d'elle même.... même si le programmeur "oublie" de faire un
Close, un Dipose ou toute autre action prévue (un peu ceinture et
bretelle)
et donc bien sûr, elle ne doit le faire qu'une fois le programme ne peut
plus la manipuler. En COM ça reviendrait à dire quand le compteur de
référence tombe à 0.

le soucis est que, pour le cas des connections, si elles ne sont pas
libérées correctement ça me pose des problèmes côté serveur

/_Simon Mourier [MS]_ a utilisé son clavier pour écrire/ :
Que cherchez vous à faire au juste? La phrase "le but étant de permettre
à la classe de faire une action particulière lorsqu'elle détecte qu'on
aura plus besoin d'elle" est particulièrement bizarre. Ce n'est pas à la
classe de détecter qu'on n'a plus besoin d'elle en général. Comment
peut-elle mourir si elle doit détecter des choses...
Simon.

"Faust" a écrit dans le message de news:

bonjour,

savez-vous s'il existe une procédure qui soit appelée lorsque que le
compteur de référence d'une instance de classe tombe à zéro (donc à
priori quand l'instance n'est plus utilisée où que ce soit et qu'elle
sera libérée par le GC)?

le but étant de permettre à la classe de faire une action particulière
lorsqu'elle détecte qu'on aura plus besoin d'elle (libération de
certaines ressources) sans que le programmeur qui utilise cette classe
soit obligé de faire lui même une gestion fastidieuse pour savoir s'il
peut faire un dispose

à moins (et c'est possible parce que j'ai pas tout compris) que le
paramètre Disposing du Dispose serve justement à ça: que le dispose est
appelé systématiquement à chaque fois qu'une variable passe "out of
scope" avec le paramètre Disposing à false tant qu'il reste des
variables "not out of scope" et passé à true dans le cas où c'est la
dernière variable qui passe "out of scope"?

-- */Teträm/*
http://www.tetram.info

"Après ton vomi, ne remange pas tout, laisses-en pour tes mouches" -
Proverbe Troll






--
*/Teträm/*
http://www.tetram.info

"Mange d'abord, defeque ensuite: tu réfléchiras plus tard" - Proverbe
Troll



Avatar
Faust
/_Simon Mourier [MS]_ a formulé ce jeudi/ :
Pour les ressources non managées (handles, connexions, etc...) , il faut
utiliser le pattern proposé par IDisposable. C'est en gros l'unique solution,
et c'est comme ca que sont gérées d'ailleurs toutes les ressources non
managées dans le .NET Framework.

Même si le programmeur oublie d'appeler classe.Dispose(), ce sera appelé
automatiquement.



oui mais quand précisément? quand le GC aura décidé de faire du ménage
parce que les ressources disponibles pour l'application sont devenues
insufisantes ou dès que la dernière variable pointant sur une instance
d'une classe perdra ce pointage?

mon problème n'est pas tant la libération de ces ressources mais le
moment de cette libération: l'occupation de ces ressources provoque des
verrous à différents niveaux de mon système. Si elles ne sont pas
libérées (quelque soit la façon dont c'est fait), les verrous
persistent et peuvent entrainer un blocage complet du système (qui ne
se limite pas à l'appli qui utilise la classe)
c'est pour ça que j'ai impérativement besoin que ces ressources soient
libérées et ce même si le programmeur oublie de le demander
explicitement et surtout le plus tôt possible (le mieux étant dès
qu'elles ne sont plus utiles)

Je ne vois pas ce qui vous manque?



une information claire peut-être?

--
*/Teträm/*
http://www.tetram.info

"Le monde est rond comme le cul d'une pucelle. On ne peut pas s'y
perdre"
Chevalier Or-Azur
Avatar
Paul Bacelar
"Faust" wrote in message
news:
/_Simon Mourier [MS]_ a formulé ce jeudi/ :
> Pour les ressources non managées (handles, connexions, etc...) , il faut
> utiliser le pattern proposé par IDisposable. C'est en gros l'unique


solution,
> et c'est comme ca que sont gérées d'ailleurs toutes les ressources non
> managées dans le .NET Framework.
>
> Même si le programmeur oublie d'appeler classe.Dispose(), ce sera appelé
> automatiquement.

oui mais quand précisément? quand le GC aura décidé de faire du ménage
parce que les ressources disponibles pour l'application sont devenues
insufisantes ou dès que la dernière variable pointant sur une instance
d'une classe perdra ce pointage?

mon problème n'est pas tant la libération de ces ressources mais le
moment de cette libération: l'occupation de ces ressources provoque des
verrous à différents niveaux de mon système. Si elles ne sont pas
libérées (quelque soit la façon dont c'est fait), les verrous
persistent et peuvent entrainer un blocage complet du système (qui ne
se limite pas à l'appli qui utilise la classe)
c'est pour ça que j'ai impérativement besoin que ces ressources soient
libérées et ce même si le programmeur oublie de le demander
explicitement et surtout le plus tôt possible (le mieux étant dès
qu'elles ne sont plus utiles)

> Je ne vois pas ce qui vous manque?

une information claire peut-être?

--
*/Teträm/*
http://www.tetram.info

"Le monde est rond comme le cul d'une pucelle. On ne peut pas s'y
perdre"
Chevalier Or-Azur




La seule solution est correctement designer vos classes de telle manière que
l'utilisateur puisse implémenter des design patterns qui lui permettent de
ne pas oublier le dispose.

Donnez-nous votre problème précis et on verra les moyens pour permettre une
utilisation sûr de vos ressources et la gestion de leurs cycles de vie.

Il ne faut pas s'appuyer sur le garbage collector mais sur une conception
soigné de vos classes.

De nombreux design patterns peuvent répondre à votre problématique mais il
nous faut plus de billes ;-).


--
Paul Bacelar
Avatar
Simon Mourier [MS]
L'ensemble du framework .NET a les même contraintes fonctionnelles
(utilisation de ressources au bon moment, etc;..), et le bon pattern est
IDisposable. La documentation de IDisposable me semble tout à fait claire
sur le sujet.

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpref/html/frlrfSystemIDisposableClassTopic.asp
http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpguide/html/cpconimplementingdisposemethod.asp

Il faut que vous construisiez vos classes autour de ce pattern, et que vous
indiquiez au programmeur appelant votre code de libérer les ressources en
appelant Dispose ou en utilisant la directive "using" (en C#). L'ensemble
des objets de GDI+ par exemple est documenté de cette façon. Si le
programmeur oublie d'appeler Dispose sur un Pen ou un Brush, il aura des
problèmes. Dans votre cas, c'est la même chose.

Simon.

"Faust" a écrit dans le message de news:

/_Simon Mourier [MS]_ a formulé ce jeudi/ :
Pour les ressources non managées (handles, connexions, etc...) , il faut
utiliser le pattern proposé par IDisposable. C'est en gros l'unique
solution, et c'est comme ca que sont gérées d'ailleurs toutes les
ressources non managées dans le .NET Framework.

Même si le programmeur oublie d'appeler classe.Dispose(), ce sera appelé
automatiquement.



oui mais quand précisément? quand le GC aura décidé de faire du ménage
parce que les ressources disponibles pour l'application sont devenues
insufisantes ou dès que la dernière variable pointant sur une instance
d'une classe perdra ce pointage?

mon problème n'est pas tant la libération de ces ressources mais le moment
de cette libération: l'occupation de ces ressources provoque des verrous à
différents niveaux de mon système. Si elles ne sont pas libérées (quelque
soit la façon dont c'est fait), les verrous persistent et peuvent
entrainer un blocage complet du système (qui ne se limite pas à l'appli
qui utilise la classe)
c'est pour ça que j'ai impérativement besoin que ces ressources soient
libérées et ce même si le programmeur oublie de le demander explicitement
et surtout le plus tôt possible (le mieux étant dès qu'elles ne sont plus
utiles)

Je ne vois pas ce qui vous manque?



une information claire peut-être?

--
*/Teträm/*
http://www.tetram.info

"Le monde est rond comme le cul d'une pucelle. On ne peut pas s'y perdre"
Chevalier Or-Azur



1 2