Re: this в замыкании
От: BogdanMart Украина  
Дата: 26.06.11 11:27
Оценка: -1
Не вижу причн не давть использовать this. скорее надо позволить его использовать в первом случае.

А кто его будет использовать там, где не надо -- его проблемы.
this в замыкании
От: catbert  
Дата: 26.06.11 10:44
Оценка:
Такой код не компилируется:
  public module Program
  {
      
    Main() : void
    {
        def x = First();
        Console.WriteLine($"$x");
    }
   
    public class Base
    {
        
    }
    
    public class First : Base
    {
      field : Second = Second(this);
    }

    public class Second
    {
      field : First;
      
      internal this(first : First)
      {
          field = first;
      }
    }     
          
  }


Ошибка компилятора:

``this'' or ``base'' usage before base is constructed


Если мы чуть изменим код:
  public module Program
  {
      
    Main() : void
    {
        def x = First();
        Console.WriteLine($"$x");
    }
   
    public class Base
    {
        
    }
    
    public class First : Base
    {
      field : Second = Second(() => this);
    }

    public class Second
    {
      field : First;
      
      internal this(first : void -> First)
      {
          field = first();
      }
    }     
          
  }


Все работает без проблем. Хотя лямбда, по идее, должна вызываться тогда же, когда в первом примере передается this, то есть опять до конструирования базового класса.

В C# аналоги обоих примеров не компилируются:

Keyword 'this' is not available in the current context


В чем тут магия?

На такое поведение компилятора можно полагаться, или это баг, который может быть исправлен?
Re: this в замыкании
От: Tissot Россия  
Дата: 26.06.11 11:41
Оценка:
Здравствуйте, catbert, Вы писали:

C>Все работает без проблем. Хотя лямбда, по идее, должна вызываться тогда же, когда в первом примере передается this, то есть опять до конструирования базового класса.


C>В C# аналоги обоих примеров не компилируются:

C>

Keyword 'this' is not available in the current context


C>В чем тут магия?


C>На такое поведение компилятора можно полагаться, или это баг, который может быть исправлен?


Корректное поведение — поведение компилятора C#-а, т.к. рабочий вариант в nemerle (с лямбдой) позволяет обратиться из внешнего кода к недоконструированному объекту.
Re[2]: this в замыкании
От: catbert  
Дата: 26.06.11 13:15
Оценка:
Здравствуйте, Tissot, Вы писали:

T>Корректное поведение — поведение компилятора C#-а, т.к. рабочий вариант в nemerle (с лямбдой) позволяет обратиться из внешнего кода к недоконструированному объекту.


На самом деле, C# тоже позволяет обратиться из внешнего кода к недоконструированному объекту:

        class First
        {

            Second field;

            public First()
            {
                field = new Second(this);
            }

        }

        class Second
        {

            First field;

            public Second(First x)
            {
                DoEveryPossibleThingWith(x)
            }

        }


Насколько я понимаю, разница в том, позволять ли доступ к объекту до вызова конструктора базового класса.
Re[3]: this в замыкании
От: Tissot Россия  
Дата: 26.06.11 13:30
Оценка:
Здравствуйте, catbert, Вы писали:

T>>Корректное поведение — поведение компилятора C#-а, т.к. рабочий вариант в nemerle (с лямбдой) позволяет обратиться из внешнего кода к недоконструированному объекту.


C>На самом деле, C# тоже позволяет обратиться из внешнего кода к недоконструированному объекту:


C>Насколько я понимаю, разница в том, позволять ли доступ к объекту до вызова конструктора базового класса.


Это уже ответственность автора этого класса. В изначальном варианте насколько я понимаю, не вызывается конструктор базового класса.
Re[4]: this в замыкании
От: BogdanMart Украина  
Дата: 26.06.11 15:08
Оценка:
Здравствуйте, Tissot, Вы писали:


T>Это уже ответственность автора этого класса. В изначальном варианте насколько я понимаю, не вызывается конструктор базового класса.


Не знал, что поля инициализируються до вызова базового конструктора (а толку от этого?)

Хотя CLR позволяет его вообще не вызывать (на уровне MSIL), a рантайм -- вызывать конструктор сколько угодно раз)
Re[5]: this в замыкании
От: catbert  
Дата: 26.06.11 18:28
Оценка:
Здравствуйте, BogdanMart, Вы писали:

BM>Здравствуйте, Tissot, Вы писали:



BM>Не знал, что поля инициализируються до вызова базового конструктора (а толку от этого?)


В спецификации C# так написано:

This ordering ensures that all instance fields are initialized by their variable initializers before any statements that have access to that instance are executed.


Мне кажется, в инициализаторах должно быть возможно все, что возможно в самом конструкторе. Поэтому base() должен вызываться самым первым (хотя тогда возникают нюансы типа this() { base(myField); }).

Судя по тому, как все сделано в Немерле, возможность использовать this в лямбде-инициализаторе — баг. Но довольно полезный баг.
Re[2]: this в замыкании
От: catbert  
Дата: 26.06.11 18:29
Оценка:
Здравствуйте, BogdanMart, Вы писали:

BM>Не вижу причн не давть использовать this. скорее надо позволить его использовать в первом случае.


this можно использовать, но не в инициализаторах полей класса.
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.