Существует ли способ вынудить статические поля быть инициализированными в C#?

Рассмотрите следующий код:

class Program
{
    static Program() {
        Program.program1.Value = 5;
    }

    static List<Program> values = new List<Program>();
    int value;
    int Value
    {
        get { return value; }
        set { 
            this.value = value;
            Program.values.Add(this);
        }
    }

    static Program program1 = new Program { value = 1 };
    static Program program2 = new Program { value = 2 };
    static Program program3 = new Program { value = 3 };

    static void Main(string[] args)
    {
        if (Program.values.Count == 0) Console.WriteLine("Empty");
        foreach (var value in Program.values)
            Console.WriteLine(value.Value);
        Console.ReadKey();
    }
}

Это печатает только номер 5 и, если удалено код в статическом конструкторе, это печатает "Пустой".

Существует ли способ вынудить статические поля быть инициализированными даже ли не используемый уже?

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

Я попробовал некоторые изменения этого кода и некоторые работы для некоторых типов, но не делаю для других.

Править: ОБРАЗЕЦ ВЫШЕ ПОВРЕЖДАЕТСЯ, ПОПРОБУЙТЕ ЭТОГО:

class Subclass<T> {
    static Subclass()
    {
        Values = new List<Subclass<T>>();
    }
    public Subclass()
    {
        if (!Values.Any(i => i.Value.Equals(this.Value)))
        {
            Values.Add(this);
        } 
    }

    public T Value { get; set; }

    public static List<Subclass<T>> Values { get; private set; }
}

class Superclass : Subclass<int>
{
    public static Superclass SuperclassA1 = new Superclass { Value = 1 };
    public static Superclass SuperclassA2 = new Superclass { Value = 2 };
    public static Superclass SuperclassA3 = new Superclass { Value = 3 };
    public static Superclass SuperclassA4 = new Superclass { Value = 4 }; 
}

class Program
{
    static void Main(string[] args)
    {
        //Console.WriteLine(Superclass.SuperclassA1); //UNCOMMENT THIS LINE AND IT WORKS
        foreach (var value in Superclass.Values)
        {
            Console.WriteLine(value.Value);
        }
        Console.ReadKey();
    }
}
7
задан Mike Cluck 27 August 2015 в 18:29
поделиться

3 ответа

Ответ на ваш вопрос - "ну, да". Но один из двух способов "навязать" это то, что вы уже делаете.

Соответствующим разделом в спецификации языка является 10.11 Статические конструкторы, а именно:

"Статический конструктор для класса выполняет максимум один раз в данной прикладной области. Выполнение статического конструктора запускается по первому из следующих событий, происходящих в домене приложения:

  • Создается экземпляр класса.
  • Ссылка на любой из статических членов класса.

Если класс содержит Главный метод (раздел 3.1), в котором начинается выполнение, то перед вызовом Главного метода для этого класса выполняется статический конструктор. Если класс содержит какие-либо статические поля с инициализаторами, то эти инициализаторы выполняются в текстовом порядке непосредственно перед вызовом статического конструктора"

.
8
ответ дан 6 December 2019 в 08:43
поделиться

На самом деле выглядит вам с ошибкой «значение» -> «значение» Так:

    static Program program1 = new Program { Value = 1 };
    static Program program2 = new Program { Value = 2 };
    static Program program3 = new Program { Value = 3 };

симпатичные принты больше линий

2
ответ дан 6 December 2019 в 08:43
поделиться

Но вы никогда не устанавливаете свойство - вместо этого вы устанавливаете поле поддержки напрямую, поэтому не выполняете свою логику для добавления в статический список при создании program1, program2 и program3.

т.е. вам необходимо изменить:

    static Program program1 = new Program { value = 1 };
    static Program program2 = new Program { value = 2 };
    static Program program3 = new Program { value = 3 };

на:

    static Program program1 = new Program { Value = 1 };
    static Program program2 = new Program { Value = 2 };
    static Program program3 = new Program { Value = 3 };
4
ответ дан 6 December 2019 в 08:43
поделиться
Другие вопросы по тегам:

Похожие вопросы: