Я ищу лучший способ предоставить метод в (абстрактном) базовом классе, который должны иметь возможность использовать все наследующие классы.
Этот метод должен ссылаться на поля и свойства наследующих типов.
Есть ли способ предоставить такой метод прототипа, который не требует от меня:

  • Передайте ссылку на каждый рассматриваемый наследующий экземпляр
  • Реализуйте метод для каждого наследующего класса, который передает ссылку на себя методу базового класса.
  • Напишите метод расширения для реализации классов

Все вышеперечисленное работает, но по-своему кажется несколько неудобным и неэлегантным.

Вот пример, в котором я реализовал три вышеуказанных метода ссылки на наследующий класс:

using System;

namespace Test
{
    public abstract class BaseClass
    {
        public void ReferenceInheriting(object InheritingInstance)
        {
            Console.WriteLine("Do things specific to the inheriting class or instance thereof: " + InheritingInstance.GetType().Name);
        }
    }
    public class Inheriting : BaseClass
    {
        public void MakeUseOfBaseClassImplementation()
        {
            base.ReferenceInheriting(this);
        }
    }
    
    public static class Extensions
    {
        public static void BeAvailableForAllImplementing(this BaseClass Inh)
        {
            Console.WriteLine("Do things specific to the inheriting class or instance thereof: " + Inh.GetType().Name);
        }
    }
    
    class program
    {
        public static void Main(string[] args)
        {
            Inheriting inh = new Inheriting();
            Console.WriteLine("Method 1: Calling the inherited method from an inheriting instance, passing a reference to the instance:");
            inh.ReferenceInheriting(inh);
            Console.WriteLine("Method 2: Implementing call to the base class's method in own class:");
            inh.MakeUseOfBaseClassImplementation();
            Console.WriteLine("Method 3: Extension method for all implementing classes:");
            inh.BeAvailableForAllImplementing();
        }
    }
}

Все три подхода дают одинаковый результат, но имеют недостатки.
Есть ли другой способ сделать это, не считая анализа информации о вызывающем абоненте?
Конечно, это не имеет большого значения, но я заинтересован в том, чтобы сделать этот метод максимально удобным для пользователя, как для реализации наследования, так и для вызова.

Спасибо!

0
Ben Philipp 24 Сен 2021 в 19:20

1 ответ

Вы можете использовать Reflection, но это своего рода оружие в крайнем случае. Идиоматический способ доступа к свойству или методу в дочернем классе - сделать его абстрактным в базовом классе.

public abstract class BaseClass
{
    public void GetInheriting()
    {
        Console.WriteLine("GetMe is: {0}", this.GetMe);
    }

    protected abstract string GetMe { get; }
}

public class Inheriting : BaseClass
{
    protected override string GetMe => "Use me in BaseClass"; 
    
    public void MakeUseOfBaseClassImplementation()
    {
        base.GetInheriting();
    }
}

public class Program
{
    static public void Main()
    {
        var o = new Inheriting();
        o.MakeUseOfBaseClassImplementation();
    }
}

Ссылка на скрипку

Выход:

GetMe is: Use me in BaseClass
0
John Wu 24 Сен 2021 в 16:58