Ребят, столкнулся с какой-то маразматической особенностью C# (на которую у MS конечно же есть объяснения), но моeй инженерной логике она не поддаётся.
Всё очень просто:
class A
{
public int P = 666;
}
class B : A
{
public int P1 = 4;
public int P2;
public B()
{
P = 13;
}
}
// где-то в коде решили создать класс B:
var b = new B { P2 = P1 + P };// ошибка прокладки между стулом и монитором!
...и..... ннна тебе поддых канпелятором!! В object initializer ни мембера P, ни P1 канпелятор НЕ ВИДИТ!
Что это за маразм?? Что за такой странный контекст вдруг образовался в элементарном инициализаторе?
Я-то (наивный) думал, что {} — это просто сокращение для b.P2 = b.P1 + b.P ! Похоже, мелкомягкие что-то там намудрили под капотом.
Примером выше я хотел иллюстрировать несколько другой маразм:
Форма из WinForms
Метод()
{
var c = new UserControl {
Left = Width / 2
};
}
Здесь в OI свойство Left КАК И ПОЛОЖЕНО — от UserControl, но Width оказывается берётся от самой формы(!!!). С какого перепоя??
Ведь Width должно браться из самого внутреннего контекста, т.е. от UserControl! Что за бредовая логика заставляет MS лезть в объемлющий контекст?
PS
А я ведь ещё на заре этой дебильной фичи предлагал: не надо этой узколобой привязки инициализатора к конструктору!! Надо, чтобы это работало как with в Паскале:
var j = new J();
// какой-то посторонний код
j init {
.p1 = 3;
.fn();// ДА! И ВЫЗОВ ФУНКЦИЙ ТОЖЕ!!
p2 = .p1;
}
var j2 = new J() init {
.p1 = p2 + 6;
}
Здесь j во-первых может инициализироваться в ЛЮБОМ месте кода, а во-вторых, чётко видно кто и откуда берётся: ".p1" — это внутренний мембер (потому что с точки),
"p2" — мембер из объемлющего контекста. Просто и универсально как лом. Что помешало неумытым "синьорам" с индийских пальм сделать это по-человечески?