Невозможно определить статическое абстрактное свойство строки

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

У меня есть абстрактный класс, который содержит статический метод, который принимает статическую строку, которую я бы хотел определить как абстрактное свойство. Проблема в том, что С# не поддерживает следующее (см. Свойства ConfigurationSectionName и Текущие):

    public abstract class ProviderConfiguration : ConfigurationSection
    {
        private const string _defaultProviderPropertyName = "defaultProvider";
        private const string _providersPropertyName = "providers";

        protected static string ConfigurationSectionName { get; }

        public static Configuration Current
        {
            get { return Configuration)ConfigurationManager.GetSection(ConfigurationSectionName); }
        }
    }

Я полагаю, что одним из способов справиться с этим было бы сделать ConfigurationSectionName НЕ абстрактным, а затем создать новое определение ConfigurationSectionName в производных классах, но это выглядит довольно хаки. Любые предложения были бы наиболее желанными.

Gratias!!!

Ответ 1

Статические члены не имеют полиморфизма, поэтому они не могут быть абстрактными.: (

Если это вам нужно, подумайте о создании объекта Singleton и прочтении свойства с этого объекта.

Ответ 2

Просто используйте new, чтобы переопределить статический метод в производном классе. Ничто из того, что делает new плохой способ для виртуальных методов и свойств, применяется, поскольку должно указываться имя типа:

public class BaseClass
{
    public static int Max { get { return 0; } }
}

public class InteriorClass : BaseClass
{
}

public class DerivedClass : InteriorClass
{
    public new static int Max { get { return BaseClass.Max + 1; } }
}

class Program
{
    static void Main(string[] args)
    {
        Console.WriteLine("BaseClass.Max = {0}", BaseClass.Max);
        Console.WriteLine("InteriorClass.Max = {0}", InteriorClass.Max);
        Console.WriteLine("DerivedClass.Max = {0}", DerivedClass.Max);
        Console.ReadKey();
    }
}

Ответ 3

Хорошо, это не совсем так, чтобы создать статическое абстрактное свойство, но вы можете добиться желаемого эффекта.

Вы можете получить это, используя generics:

public abstract class MyAbstractClass<T>
{
    public static string MyAbstractString{ get; set; }
    public static string GetMyAbstracString()
    {

        return "Who are you? " + MyAbstractString;

    }
}

public class MyDerivedClass : MyAbstractClass<MyDerivedClass>
{
    public static new string MyAbstractString
    { 
        get 
        { 
            return MyAbstractClass<MyDerivedClass>.MyAbstractString; 
        }
        set
        {
            MyAbstractClass<MyDerivedClass>.MyAbstractString = value;            
        }
    }

}


public class MyDerivedClassTwo : MyAbstractClass<MyDerivedClassTwo>
{
    public static new string MyAbstractString
    {
        get
        {
            return MyAbstractClass<MyDerivedClassTwo>.MyAbstractString;
        }
        set
        {
            MyAbstractClass<MyDerivedClassTwo>.MyAbstractString = value;
        }
    }

}


public class Test
{

    public void Test()
    {

        MyDerivedClass.MyAbstractString = "I am MyDerivedClass";
        MyDerivedClassTwo.MyAbstractString = "I am MyDerivedClassTwo";


        Debug.Print(MyDerivedClass.GetMyAbstracString());
        Debug.Print(MyDerivedClassTwo.GetMyAbstracString());


    }

}

Итак, вызывая тестовый класс, вы получите:

"Кто ты? Я - MyDerivedClass" "Кто ты? Я - MyDerivedClassTwo"

Итак, у вас есть статический метод в абстрактном классе, но абстрактное значение отличается для каждого производного класса, nice: D

Итак, что здесь происходит? Трюк - это общий тег, компилятор генерирует другой абстрактный класс для каждого производного типа.

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

Ответ 4

То, что вы пытаетесь сделать, невозможно, как говорили другие.

Я бы попробовал что-то вроде этого

public abstract class ProviderConfiguration : ConfigurationSection
{
    public string ConfigurationSectionName { get; set; }

    public static ProviderConfiguration Provider { get; set; }

    public static Configuration Current
    {
        get { return (Configuration)ConfigurationManager.GetSection(Provider.ConfigurationSectionName); }
    }
}

Тогда на практике:

public void DoStuff()
{
    var provider = new DerivedProviderConfiguration();
    ProviderConfiguration.Provider = provider;
}