¿Cuál es la diferencia entre implementar una Interfaz explícita o implícitamente?

42

En Visual Studio puedo hacer clic con el botón derecho en una interfaz y elegir Implementar interfaz o Implementar interfaz explícitamente.

public class Test : ITest
{
    public string Id // Generated by Implement Interface
    {
        get { throw new NotImplementedException(); }
    }

    string ITest.Id // Generated by Implement Interface Explicitly
    {
        get { throw new NotImplementedException(); }
    }
}

La única diferencia que veo entre los dos es que el nombre de la interfaz se agrega a las propiedades y los métodos de la interfaz cuando se crean si elige Implementar la interfaz explícitamente.

Encuentro que hace que el código sea un poco más legible ya que puedo ver de dónde proviene ese método / propiedad, sin embargo, ¿esto hace alguna diferencia en la forma en que se usa o compila la clase? ¿Y realmente importa si implemento mis interfaces implícita o explícitamente?

    
pregunta Rachel 22.02.2012 - 15:29

4 respuestas

35

Revise la respuesta principal de Andrew Barrett para " implícita vs implementación explícita de la interfaz "en SO .

Básicamente:

  • Implícito: accede a los métodos y propiedades de la interfaz como si fueran parte de la clase.
  • Explícito: solo puede acceder a métodos y propiedades cuando trata a la clase como la interfaz implementada.

Ejemplos de código:

Implícito:

Test t = new Test();
t.Id; // OK
((ITest)t).Id; // OK

Explícito:

Test t = new Test();
t.Id; // Not OK
((ITest)t).Id; // OK

En términos de "cuándo" debe implementar una interfaz explícitamente, es cuando su clase ya tiene un método con la misma firma que uno de los métodos de su interfaz, o cuando su clase implementa varias interfaces que comparten métodos con las mismas firmas.

    
respondido por el Jalayn 22.02.2012 - 15:36
8

También hay una diferencia en cómo llamas al método.

Al usar una implementación de interfaz explícita , debe usar el tipo de interfaz para poder llamar a esa implementación específica.

Por lo tanto, al llamar al código, deberías usar una variable de tipo ITest para acceder a ITest.Id .

El artículo Implementación de interfaz explícita (Guía de programación de C #) en MSDN tiene un buen ejemplo.

    
respondido por el Oded 22.02.2012 - 15:34
3

Le permite implementar dos interfaces que definen el mismo método. Sin embargo, si implementa explícitamente la interfaz, solo se puede acceder a los métodos cuando se escribe la variable en esa interfaz explícita.

Consulte: Tutorial de implementación de interfaz explícita

    
respondido por el unholysampler 22.02.2012 - 15:35
3

EDITAR: No debería hacer una diferencia No deberías hacerlo a menos que tu clase implemente dos interfaces con las mismas propiedades, ya que tendrás que pasar a la interfaz relevante antes puedes acceder al miembro:

public interface ITest
{
    string Id { get; }
}

public interface IAlsoTest
{
    string Id { get; }
}

public interface ITestToo
{
    int Id { get; }
}

public class Test : ITest, IAlsoTest
{
    // Valid implicit implementation of BOTH interfaces
    public string Id
    {
        get { throw new NotImplementedException(); }
    }
}

public class TestSeparately : ITest, ITestToo
{
    // This way we can do different things depending
    // on which interface the callee called from.
    string ITest.Id
    {
        get { throw new NotImplementedException(); }
    }

    int ITestToo.Id
    {
        get { throw new NotImplementedException(); }
    }
}

public class TestOuch
{
    public void DoStuff()
    {
        var ts = new TestSeparately();

        // Works
        Console.WriteLine(((ITest)ts).Id);

        // Works
        Console.WriteLine(((ITestToo)ts).Id);

        // Not valid! Which one did we want to call?
        Console.WriteLine(ts.Id);
    }
}

El uso del ejemplo se mantiene cuando implementas explícitamente un miembro de la interfaz incluso si solo usas una única interfaz (que siempre olvido: S), así que intentaré evitar la implementación explícita siempre que sea posible, ya que ocultará a los miembros de la clase si no están asignados a la interfaz correcta (lo que es bastante confuso).

    
respondido por el Ed James 22.02.2012 - 15:38

Lea otras preguntas en las etiquetas