¿Cómo reutilizar el código cuando la herencia múltiple no es una opción?
-
05-07-2019 - |
Pregunta
Me gustaría usar algunos métodos de algunas de mis antiguas clases probadas en mi nueva clase que estoy construyendo. Desafortunadamente, C # no admite herencia múltiple. ¿Cómo puedo reutilizar el código de estas clases antiguas? ¿Acabo de crearlos como objetos miembros? o ¿Tengo otras opciones?
Solución
En general, usar la composición en lugar de la herencia es el camino a seguir, sí. Sin embargo, si pudiera dar un ejemplo concreto del tipo de cosa que quiere decir, sería más fácil ayudar a encontrar el enfoque apropiado: no siempre es lo mismo.
Otros consejos
Usarlos como objetos miembros debería ser una buena idea. Luego, también puede exponer solo los métodos de interés y adaptarlos si es necesario.
Puedes recrearlos luego como métodos de extensión cuando funcionan en el mismo tipo.
public static void MyMethod( this MyType target ){}
MyType.MyMethod()
como se indica a continuación, si tiene una clase que se deriva de MyType o implementa más la interfaz en la que funciona el método de extensión, la extensión funciona para esos.
public class MyDerived : MyType{}
MyDerived.MyMethod()
Técnicamente, C # implementa múltiples herencias interfaz , pero no múltiples implementación herencia.
El problema con la herencia de implementación múltiple es que conduce a situaciones como el problema del diamante .
Puedes simular la herencia de implementación múltiple usando una interfaz múltiple herencia y composición, que está cerca de lo que describiste como creación los objetos que desea reutilizar " como objetos miembros " ;. Lo que no quieres para hacer, sin embargo, es exponer un comportamiento innecesario de su tipo envuelto.
A continuación se muestra un diagrama de clase que muestra el principio básico de múltiples Herencia a través de la composición:
Herencia múltiple http://www.freeimagehosting.net/uploads/cb219cefba.jpg
El inconveniente de esto es que cualquier cambio en la interfaz que IBreeper requerirá cambios correspondientes a Breeper, y viceversa.
Sin embargo, retrocediendo un paso, debe observar cuidadosamente las razones de componiendo las clases antiguas. Es para:
-
Mejora o mejora el comportamiento existente. Luego, debe considerar el patrón de proxy ;
-
Cree una " ventanilla única " por todo tu comportamiento Realmente solo deberías estar haciendo esto si tu SuperFuddler es cohesivo (es decir, todo el comportamiento expuesto está alineado), de lo contrario, estarás moviéndote a Objeto de Dios que no es propicio para su mantenimiento;
-
Presente una interfaz que sea más consistente con un modo de uso requerido por cierta clase de clientes de su SuperFuddler. En este caso, debe considerar el Patrón del adaptador .
Puedes fingirlo fácilmente como esto:
public interface IFoo {
void DoFoo();
}
public class Foo : IFoo {
public void DoFoo() { Console.Write("Foo"); }
}
public class Bar {
public void DoBar() { Console.Write("Bar"); }
}
public class FooBar : IFoo, Bar {
private IFoo baseFoo = new Foo();
public void DoFoo() { baseFoo.DoFoo(); }
}
//...
FooBar fooBar = new FooBar();
fooBar.DoFoo();
fooBar.DoBar();
Si los ha desarrollado como un componente, utilícelos, no los herede