c# - una - Función base de llamada y luego función heredada
probar funcion en sql server (6)
Tengo una clase base y una clase que hereda base. La clase base tiene varias funciones virtuales que la clase heredada puede anular. Sin embargo, las funciones virtuales en la clase base tienen un código que DEBE ejecutarse antes de que se llame a las anulaciones de clases heredadas. ¿Hay alguna forma de que pueda llamar primero a las funciones virtuales de las clases base y luego anular las clases heredadas? Sin hacer una llamada a base.function ().
Sé que puedo simplemente hacer dos funciones, una que se llama, la otra virtual. Pero, ¿hay alguna manera de que pueda mantener los mismos nombres? Sé que podría necesitar cambiar algunas cosas.
class myBase
{
public virtual myFunction()
{ /* must-run code, Called first */ }
}
class myInherited : myBase
{
public override myFunction()
{ /* don''t use base.myFunction();,
called from base.myFunction(); */ }
}
Pregunta similar here .
¿Qué piensas de esto?
class myBase
{
public void myFunctionWrapper()
{
// do stuff that must happen first
// then call overridden function
this.myFunction();
}
public virtual void myFunction(){
// default implementation that can be overriden
}
}
class myInherited : myBase
{
public override void myFunction()
{
}
}
C # no tiene soporte para aplicarlo automáticamente, pero puede aplicarlo utilizando el patrón de método de plantilla . Por ejemplo, imagina que tienes este código:
abstract class Animal
{
public virtual void Speak()
{
Console.WriteLine("I''m an animal.");
}
}
class Dog : Animal
{
public override void Speak()
{
base.Speak();
Console.WriteLine("I''m a dog.");
}
}
El problema aquí es que cualquier clase que hereda de Animal
necesita llamar a base.Speak();
para garantizar que se ejecuta el comportamiento de base. Puede aplicar esto de forma automática tomando el siguiente enfoque (ligeramente diferente):
abstract class Animal
{
public void Speak()
{
Console.WriteLine("I''m an animal.");
DoSpeak();
}
protected abstract void DoSpeak();
}
class Dog : Animal
{
protected override void DoSpeak()
{
Console.WriteLine("I''m a dog.");
}
}
En este caso, los clientes solo ven el método polimórfico Speak
, pero se garantiza que se ejecutará el comportamiento Animal.Speak
. El problema es que si tienes más herencia (por ejemplo, class Dachshund : Dog
), tienes que crear otro método abstracto si quieres que se Dog.Speak
.
No exactamente. Pero he hecho algo similar usando métodos abstractos.
Los métodos abstractos deben ser anulados por clases derivadas. Los procs abstractos son virtuales, por lo que puede estar seguro de que cuando la clase base los llama, se llama a la versión de la clase derivada. Luego haga que el "Código de ejecución obligatoria" de su clase base llame al proceso abstracto después de ejecutar. voila, el código de su clase base siempre se ejecuta primero (asegúrese de que el proc de la clase base ya no sea virtual) seguido del código de su clase derivada.
class myBase
{
public /* virtual */ myFunction() // remove virtual as we always want base class''s function called here
{ /* must-run code, Called first */
// call derived object''s code
myDerivedMustcallFunction();
}
public abstract myDerivedMustCallFunction() { /* abstract functions are blank */ }
}
class myInherited : myBase
{
public override myDerivedMustCallFunction()
{ /* code to be run in derived class here */ }
}
No hay forma de hacer lo que está buscando, aparte de las 2 formas que ya mencionó.
O bien haces 2 funciones en la clase base, una que se llama y la otra virtual.
O llama a base.functionName en la subclase.
Una solución común que se puede encontrar en .NET Framework es dividir un método en un método público XXX
y un método virtual protegido OnXXX
que es llamado por el método público. Para su ejemplo, se vería así:
class MyBase
{
public void MyMethod()
{
// do something
OnMyMethod();
// do something
}
protected virtual void OnMyMethod()
{
}
}
y
class MyInherited : MyBase
{
protected override void OnMyMethod()
{
// do something
}
}
public abstract class BaseTemp
{
public void printBase() {
Console.WriteLine("base");
print();
}
public abstract void print();
}
public class TempA: BaseTemp
{
public override void print()
{
Console.WriteLine("TempA");
}
}
public class TempB: BaseTemp
{
public override void print()
{
Console.WriteLine("TempB");
}
}