Выбор ответа Senior ООП в C# обновлено

Вызов виртуального метода из конструктора

Вопрос

Что выведет new Derived()?

class Base
{
    public Base() { Print(); }
    protected virtual void Print() { }
}
class Derived : Base
{
    private int _value;
    public Derived() { _value = 42; }
    protected override void Print() => Console.WriteLine(_value);
}

Попробуйте сами

Выберите вариант, и откроется разбор.

Показать ответ и разбор

Коротко

Правильный ответ: 0. Сначала выполняются инициализаторы полей наследника, затем конструктор базы, затем тело конструктора наследника.

Варианты ответа

  1. 42
  2. NullReferenceException
  3. 0правильный ответ
  4. Ошибка компиляции: нельзя вызывать virtual из конструктора

Разбор

Сначала выполняются инициализаторы полей наследника, затем конструктор базы, затем тело конструктора наследника. Здесь _value присваивается в теле конструктора Derived, а базовый конструктор уже вызывает переопределённый Print у не до конца созданного объекта: поле ещё 0. Если бы _value = 42 было инициализатором поля, вывелось бы 42, потому что инициализаторы полей в C# идут до вызова базового конструктора. Компилятор такое разрешает, анализаторы предупреждают (CA2214).

Ответьте сами, а не прочитайте

В тренажёре вопрос попадёт в повторения и вернётся, когда начнёт забываться. Плюс билеты с зачётом: 20 вопросов, не больше 2 ошибок.

Термины по теме