44

J'ai une classe générique pour laquelle j'essaye d'implémenter le type de casting implicite. Bien que cela fonctionne principalement, cela ne fonctionnera pas pour le casting d'interface. Après une enquête plus approfondie, j'ai trouvé qu'il y a une erreur de compilation: "Conversion définie par l'utilisateur de l'interface" qui s'applique. Même si je comprends que cela devrait être appliqué dans certains cas, ce que j'essaie de faire semble être un cas légitime.Opérateur implicite utilisant des interfaces

Voici un exemple:

public class Foo<T> where T : IBar 
{ 
    private readonly T instance; 

    public Foo(T instance) 
    { 
     this.instance = instance; 
    } 
    public T Instance 
    { 
     get { return instance; } 
    } 
    public static implicit operator Foo<T>(T instance) 
    { 
     return new Foo<T>(instance); 
    } 
} 

Code pour l'utiliser:

var concreteReferenceToBar = new ConcreteBar(); 
IBar intefaceReferenceToBar = concreteReferenceToBar; 
Foo<ConcreteBar> concreteFooFromConcreteBar = concreteReferenceToBar; 
Foo<IBar> fooFromConcreteBar = concreteReferenceToBar; 
Foo<IBar> fooFromInterfaceBar = intefaceReferenceToBar; // doesn't work 

Est-ce que quelqu'un sait contourner ce problème, ou peut-on expliquer de manière satisfaisante pourquoi je shuouldn't être en mesure de jeter interfaceReferenceToBar implicitement à Foo<IBar>, puisque dans mon cas, il n'est pas converti, mais seulement contenu dans Foo?

EDIT: Il semble que la covariance puisse offrir le salut. Espérons que la spécification C# 4.0 permette le cast implicite des types d'interface en utilisant la covariance.

Répondre

46

La raison pour laquelle vous ne pouvez pas le faire parce qu'il est spécifiquement interdit dans la spécification du langage C#:

A class or struct is permitted to declare a conversion from a source type S to a target type T provided all of the following are true:

  • ...
  • Neither S nor T is object or an interface-type.

et

User-defined conversions are not allowed to convert from or to interface-types. In particular, this restriction ensures that no user-defined transformations occur when converting to an interface-type, and that a conversion to an interface-type succeeds only if the object being converted actually implements the specified interface-type.

Source

+0

Je comprends que cela fait partie de la spécification, le casting implicite d'une interface devrait être invalide dans certains cas, mais dans tous? –

+0

Je suis d'accord avec vous, je ne sais pas pourquoi ils l'ont rendu invalide pour tous les cas. Dans ce cas, vous pouvez déterminer au moment de la compilation que la distribution est (devrait être) valide. –

+3

Je * pense * que la restriction sur la coulée d'interface implicite est liée à la façon dont COM Interop est implémenté. COM utilise QueryInterface, que .NET gère automatiquement. Autoriser la conversion d'interface implicite interférerait. – Mark

Questions connexes