Specified cast is not valid.

Minotthor
Messages postés
72
Date d'inscription
vendredi 16 mai 2003
Statut
Membre
Dernière intervention
12 août 2009
- 16 oct. 2005 à 01:10
Minotthor
Messages postés
72
Date d'inscription
vendredi 16 mai 2003
Statut
Membre
Dernière intervention
12 août 2009
- 16 oct. 2005 à 14:12
Tout d'abord, trois petites question :



Est-il possible d'hériter d'une classe dont tous les constructeurs sont
"private" ? En fait elle crée ses instances à partir d'une méthode
statique sur le schema de System.Reflection. Assembly
System.Reflection.Assembly.LoadFrom (string).



Quand une exception survient dans un constructeur, qu'advient-il de
l'instance que ce constructeur était censé initialiser ? Je m'explique
: si j'étais sûr qu'en cas d'erreur ce sera bien un null qui sera
retourné par la new à la référence et pas l'adresse d'une instance à
moitié initialisée, inutilisable et provoquant des erreurs en série, je
pourrais me passer d'utiliser une ****** de methode statique comme
substitut au constructeur.



Est-il possible de forcer un constructeur à renvoyer null à la
référence dans un cas particulier comme on ferait un return null dans
une méthode classique ?



Ensuite, plus compliqué :-p !



C'est un système de classes destiné à l'internationalisation (programme
polyglotte). La classe de base est Excubitor.Binders.LateBinder (je
n'inclus pas le code des méthodes pour ne pas encombrer mais si il vous
intéresse n'hésitez pas à le demander, j'enverrai les fichiers du
projet et de toute façon tout sera posté sur ce site quand je jugerai le travail digne d'intérêt) :



La classe de base :



namespace Excubitor.Binders

{

public class LateBinder

{

private System.Reflection.Assembly Assembly ;

private System.Type Type ;

private object Instance ;



protected internal LateBinder () {}



public static LateBinder Load (string Path, string Type) {[...]}



protected object InvokeMethod (string Name, object[] Arguments) {[...]}



public static event Excubitor.Delegates.ExceptionHandler AssemblyLoadingFailed ;

public static event Excubitor.Delegates.ExceptionHandler TypeLoadingFailed ;

public static event Excubitor.Delegates.ExceptionHandler InstanceCreationFailed ;



public event Excubitor.Delegates.MethodInvokeExceptionHandler MethodInvocationFailed ;

}

[...]

}



Les délégates en question (même si je doute que le problème vienne de la) :



namespace Excubitor.Delegates

{

public delegate void ExceptionHandler (object Sender, System.Exception Exception) ;

public delegate void MethodInvokeExceptionHandler
(object Sender, System.Exception Exception, string Name, object[]
Arguments) ;

[...]

}



Voici maintenant un exemple d'héritage :



namespace Excubitor.Sodalitas.Languages

{

public interface Language

{

string Hello () ;

}

}



namespace Excubitor.Sodalitas.Sodalitas

{

public class LateLanguageBinder : Excubitor.Binders.LateBinder, Excubitor.Sodalitas.Languages.Language

{

public string Hello ()

{

return (string) (this.InvokeMethod ("Hello", null)) ;

}

}



}



Et la librairie qui va avec :



namespace Excubitor.Sodalitas.Languages

{

class French : Language

{

public string Hello ()

{

return "Bonjour" ;

}

}

}



L'intérêt est évidemment de pouvoir gérer des languages complexes en
composant les phrases à l'aide d'arguments passés à la méthode,
d'appeler cette méthode comme s'il s'agissait d'une méthode locale
("Language.Hello ()") et ce sans même savoir quelle DLL a été
late-bound.



Mais c'est là que ça cloche :



LateLanguageBinder Language = LateLanguageBinder.Load
(@"E:\Programmation\Excubitor\Sodalitas\Languages\French\bin\Debug\French.dll",
"Excubitor.Sodalitas.Languages.French") ;



E:\Programmation\Excubitor\Sodalitas\Sodalitas\MainClass.cs(7): Cannot
implicitly convert type 'Excubitor.Binders.LateBinder' to
'Excubitor.Sodalitas.Sodalitas.LateLanguageBinder'



Ceci ne râle pas à la compilation mais plante à l'exécution :



LateLanguageBinder Language = (LateLanguageBinder)
LateLanguageBinder.Load
(@"E:\Programmation\Excubitor\Sodalitas\Languages\French\bin\Debug\French.dll",
"Excubitor.Sodalitas.Languages.French") ;



An unhandled exception of type 'System.InvalidCastException' occurred in Sodalitas.exe



Additional information: Specified cast is not valid.



Je comprends le problème : j'essaye de faire passer un cube dans un trou triangulaire et .NET n'aime pas ça !



Mais la solution ... je sèche. Et vous ?

4 réponses

Lutinore
Messages postés
3246
Date d'inscription
lundi 25 avril 2005
Statut
Membre
Dernière intervention
27 octobre 2012
42
16 oct. 2005 à 11:23
Salut, utilises un constructeur protected pour dériver ta classe. En cas d'exception dans un constucteur l'object n'est pas créé, ( à moins de catcher l'exception à l'interieur du ctor. ) Pour les ctor statics c'est différent une TypeInitialisationException est lancée.
0
cs_coq
Messages postés
6351
Date d'inscription
samedi 1 juin 2002
Statut
Membre
Dernière intervention
2 août 2014
99
16 oct. 2005 à 11:26
Salut,

Normalement oui ce sera null.
Sinon :
MaClasse monInstance;
try
{
monInstance = new MaClasse();
}
catch
{
monInstance = null;
}

Pour ton 2eme problème, tu peux peut être essayer de mettre en place une conversion explicite afin qu'un "Langage" puisse être converti en "LateLanguageBinder" sans relation d'héritage entre eux.
http://msdn.microsoft.com/library/fre/default.asp?url=/library/fre/csref/html/vclrfExplicit.asp

Mais là je ne vois pas pourquoi tu ne te sert pas de l'interface "Langage" définie justement, ils l'implémentent tous les 2 ?

/*
coq
MVP Visual C#
*/
0
Lutinore
Messages postés
3246
Date d'inscription
lundi 25 avril 2005
Statut
Membre
Dernière intervention
27 octobre 2012
42
16 oct. 2005 à 11:41
On peu caster une classe derivée vers sa classe de base, mais l'inverse n'est pas possible.
0
Minotthor
Messages postés
72
Date d'inscription
vendredi 16 mai 2003
Statut
Membre
Dernière intervention
12 août 2009
2
16 oct. 2005 à 14:12
Merci pour votre aide.



Je vais faire une série de tests pour vérifier la fiabilité des valeurs de retour des constructeurs.
0