Здравствуйте, WFrag, Вы писали:
WF>Точка создания. Контекст — штука динамическая, при одном вызове метода create переменная val (имя val) связана (т.н биндинг) с одной областью хранения (некоторое место в стеке), при втором вызове — с другой. Вот эти биндинги и запоминаются. В общем, забей.
Продемонстрируй мне, плиз, на любом языке (на шпрпе так вообще замечательно бедет) как меняется контекст от вызова.
WF>Кстати, цитата из Википедии: WF>[quote] WF>Support for closures is introduced in version 2.0 of C#. In C#, they are called "anonymous methods". WF>[/quote]
Там тоже кто хочет тот и пишет.
WF>Нет, именно сущность под названием "замыкание". Функция + контекст = замыкание.
Мне этот спор надоел. Думаю ты понял о чем я говорю.
... << RSDN@Home 1.1.4 beta 7 rev. 466>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, Трурль, Вы писали:
Т>Здравствуйте, VladD2, Вы писали:
VD>>Так вот замыкание — это метод с контекстом. Выразить это можно как указатель на метод. Вот делегат и является таким указателем.
Т>Замыкание — действительно метод с контекстом, а делегат — указатель на метод. Но вот выразить "метод с контекстом" как "указатель на метод" не получится. Поэтому делегаты — не замыкания.
В каком-то смысле согласен. Делегат и клосюр в дельфи — это конечно указатель. Именно по этому мне не очень нравится применение этого термина. Экземпляр функционального типа или делегата будет по понятнее. Ну, и метод + анонимный метод или функция и лямбда для описания самих функций тоже.
... << RSDN@Home 1.1.4 beta 7 rev. 466>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, VladD2, Вы писали:
VD>Продемонстрируй мне, плиз, на любом языке (на шпрпе так вообще замечательно бедет) как меняется контекст от вызова.
Для начала определю, что контекст — это множество пар <имя, область хранения>, т.е множество биндингов. Наверное, это следовало бы сделать сразу.
Возьмем код, приведенный выше:
using System;
public class Test
{
public delegate int retInc();
public static void Main(string[] args) {
retInc func = create();
retInc func2 = create();
Console.WriteLine(func());
Console.WriteLine(func2());
}
public static retInc create() {
int val = 0;
return delegate () {
return val++;
};
}
}
Этот код выведет два раза 0. Почему? Потому что оба раза, когда создавались замыкания (при первом вызове create и при втором) контекст был _разный_, т.е переменная — одна (одно имя), но при двух разных вызовах переменная связывалась с разными областями хранения (с точки зрения семантики, детали реализации не интерсны). Если бы мы создали оба замыкания во время одного вызова create:
using System;
public class Test
{
public delegate int retInc();
public static void Main(string[] args) {
retInc func1, func2;
create(out func1, out func2);
Console.WriteLine(func1());
Console.WriteLine(func2());
}
public static void create(out retInc f1, out retInc f2) {
int val = 0;
f1 = delegate () {
return val++;
};
f2 = delegate () {
return val++;
};
}
}
То контекст у обоих замыканий был бы один и тот же, как результат — получаем вывод 0 и 1.
>Мне этот спор надоел. Думаю ты понял о чем я говорю.
Здравствуйте, WFrag, Вы писали:
WF>Для начала определю, что контекст — это множество пар <имя, область хранения>, т.е множество биндингов. Наверное, это следовало бы сделать сразу.
Нет. Для начала мы определимся, что контекст — это набор перепенных доступной и некоторой точки.
Все остальное соотвественно смысла не имеет.
... << RSDN@Home 1.1.4 beta 7 rev. 466>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
VladD2,
> ПК> Меняется: копирование становится скрытым, неочевидным. > > А в С++ что-то было очевидным и не скрытым?
Время жизни объектов. Если последовать твоему предложению, и начать неявно копировать контекст, время жизни объектов начнет непредсказуемо изменяться только из-за того, что их кто-то решил их использовать в анонимной функции.
Posted via RSDN NNTP Server 2.0 beta
Легче одурачить людей, чем убедить их в том, что они одурачены. — Марк Твен
Здравствуйте, VladD2, Вы писали:
VD>Нет. Для начала мы определимся, что контекст — это набор перепенных доступной и некоторой точки.
Тогда весь разговор смысла вообще не имеет. Потому как замыкания захватывают именно динамический контекст, так, как я его определил. Это и есть смысл замыканий — захват биндингов переменных (тех, которые находятся в области видимости) в рантайме. И "контекст" я употреблял именно в смысле биндингов.
VD>Все остальное соотвественно смысла не имеет.
Здравствуйте, WFrag, Вы писали: WF>Насколько я помню, в Дельфи вроде бы можно функции одна в другую вкладывать.
Можно WF>Можно ли сделать так, чтобы две вложенные функции (например, InnerA и InnerB) общались через локальную переменную во "внешней" функции.
Можно. WF>Псевдо-код (Дельфи плохо знаю). WF>Так вот. Если эти A и B вернуть наружу Outer, то вызывая их по-очереди, что получим?
Ничего. Взять адрес вложенной функции нельзя. У нее нет собственного фрейма стека.
... << RSDN@Home 1.1.4 beta 5 rev. 395>>
Уйдемте отсюда, Румата! У вас слишком богатые погреба.
Здравствуйте, Sinclair, Вы писали:
S>Здравствуйте, WFrag, Вы писали: WF>>Насколько я помню, в Дельфи вроде бы можно функции одна в другую вкладывать. S>Можно WF>>Можно ли сделать так, чтобы две вложенные функции (например, InnerA и InnerB) общались через локальную переменную во "внешней" функции. S>Можно. WF>>Псевдо-код (Дельфи плохо знаю). WF>>Так вот. Если эти A и B вернуть наружу Outer, то вызывая их по-очереди, что получим? S>Ничего. Взять адрес вложенной функции нельзя. У нее нет собственного фрейма стека.
Ага. Понятно. То есть замыканий все-таки нет. Вложенные функции получается и не функции в общем-то.
Здравствуйте, Павел Кузнецов, Вы писали:
>> А в С++ что-то было очевидным и не скрытым?
ПК>Время жизни объектов. Если последовать твоему предложению, и начать неявно копировать контекст, время жизни объектов начнет непредсказуемо изменяться только из-за того, что их кто-то решил их использовать в анонимной функции.
Да уж... как всё запущено
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
Если нам не помогут, то мы тоже никого не пощадим.
IT,
> ПК> Время жизни объектов. Если последовать твоему предложению, и начать неявно копировать контекст, время жизни объектов начнет непредсказуемо изменяться только из-за того, что их кто-то решил их использовать в анонимной функции.
> Да уж... как всё запущено
Если время вызова деструктора существенно, это может иметь весьма разрушительные последствия, еще и трудно обнаружимые. Представь, что вызов Dispose() вдруг начнет происходить не там, где кончается блок using, а в каком-то другом месте. При этом для того, чтоб это произошло достаточно просто сослаться на данный объект где-то в одном из блоков внутри using...
Впрочем, не все так страшно, если ввести специальный синтаксис для копирующих ссылок на контекст, чтоб в точке использования переменной из окружающего блока было видно, что она будет скопирована.
Posted via RSDN NNTP Server 2.0 beta
Легче одурачить людей, чем убедить их в том, что они одурачены. — Марк Твен
Здравствуйте, Павел Кузнецов, Вы писали:
ПК>Впрочем, не все так страшно, если ввести специальный синтаксис для копирующих ссылок на контекст, чтоб в точке использования переменной из окружающего блока было видно, что она будет скопирована.
А зачем вообще копировать что-то в контекст? Чем ссылки не устраивают?
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
Если нам не помогут, то мы тоже никого не пощадим.
IT,
> ПК>Впрочем, не все так страшно, если ввести специальный синтаксис для копирующих ссылок на контекст, чтоб в точке использования переменной из окружающего блока было видно, что она будет скопирована. > > А зачем вообще копировать что-то в контекст? Чем ссылки не устраивают?
Копирование предложил Влад в качестве решения другой проблемы, проблемы выхода контекста из области видимости < http://rsdn.ru/forum/?mid=1241014
>. Будет происходить, например, если где-то запомнить или вернуть из функции делегат, проинициализированный анонимной функцией, использующей локальные переменные "родительской" функции. Т.е., если контекст в замыкание не копировать, а только ссылаться на него, он может "умереть" до конца жизни замыкания, если копировать — появляются проблемы с неявным копированием, временем жизни и т.п.
Posted via RSDN NNTP Server 2.0 beta
Легче одурачить людей, чем убедить их в том, что они одурачены. — Марк Твен
Здравствуйте, Павел Кузнецов, Вы писали:
ПК>Время жизни объектов. Если последовать твоему предложению, и начать неявно копировать контекст, время жизни объектов начнет непредсказуемо изменяться только из-за того, что их кто-то решил их использовать в анонимной функции.
Ты ничего не путашь? В С++ никогда наличие ссылок не определяло время жизни. Все будет как и раньше. Сылки на мертвые объекты и ручное управление жизнью, тобы это происходило по реже.
... << RSDN@Home 1.1.4 beta 7 rev. 466>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, Павел Кузнецов, Вы писали:
ПК>Копирование предложил Влад в качестве решения другой проблемы, проблемы выхода контекста из области видимости < http://rsdn.ru/forum/?mid=1241014
>. Будет происходить, например, если где-то запомнить или вернуть из функции делегат, проинициализированный анонимной функцией, использующей локальные переменные "родительской" функции. Т.е., если контекст в замыкание не копировать, а только ссылаться на него, он может "умереть" до конца жизни замыкания, если копировать — появляются проблемы с неявным копированием, временем жизни и т.п.
Это таже проблема что и передача в функцию локальной переменной по ссылке. С ней бесполезно бороться.
... << RSDN@Home 1.1.4 beta 7 rev. 447>>
Если нам не помогут, то мы тоже никого не пощадим.
VladD2,
> ПК> Время жизни объектов. Если последовать твоему предложению, и начать неявно копировать контекст, время жизни объектов начнет непредсказуемо изменяться только из-за того, что их кто-то решил их использовать в анонимной функции.
> Ты ничего не путашь? В С++ никогда наличие ссылок не определяло время жизни. Все будет как и раньше. Сылки на мертвые объекты и ручное управление жизнью, тобы это происходило по реже.
1) Наличие ссылок в определенных случаях влияет на время жизни (привязка rvalue к константным ссылкам).
2) Ты предложил копировать контекст: "Что значит помрет? Метод получит копию."
Здравствуйте, WFrag, Вы писали: WF>Ага. Понятно. То есть замыканий все-таки нет. Вложенные функции получается и не функции в общем-то.
Да. Все, что можно замкнуть в Delphi — это ссылку на экземпляр объекта, на котором выполняется данный метод.
... << RSDN@Home 1.1.4 beta 5 rev. 395>>
Уйдемте отсюда, Румата! У вас слишком богатые погреба.
Здравствуйте, Sinclair, Вы писали:
S>Здравствуйте, WFrag, Вы писали: WF>>Ага. Понятно. То есть замыканий все-таки нет. Вложенные функции получается и не функции в общем-то. S>Да. Все, что можно замкнуть в Delphi — это ссылку на экземпляр объекта, на котором выполняется данный метод.
"Всего то" К этому всему-то приципили виртуальные конструкторы/фабрики, примитивнийший рефлекшон и получилась самодостаточная среда для компонентного программирования не требующая костылей вроде КОМ-а.
Плюсам бы такое "всего то". Ну, или Дельфям шаблоны с операторами.
... << RSDN@Home 1.1.4 beta 7 rev. 466>>
Есть логика намерений и логика обстоятельств, последняя всегда сильнее.
Здравствуйте, VladD2, Вы писали: VD>"Всего то" К этому всему-то приципили виртуальные конструкторы/фабрики, примитивнийший рефлекшон и получилась самодостаточная среда для компонентного программирования не требующая костылей вроде КОМ-а.
Конечно. Потому как в реальной жизни паттерн "делегат", т.е. указатель на метод + указатель на объект, встречается гораздо чаще, чем всё остальное вместе взятое. В Delphi взяли наиболее популярные паттерны визуальной разработки и засунули в язык. VD>Плюсам бы такое "всего то". Ну, или Дельфям шаблоны с операторами.
Ну, я бы предпочел паттерн типа "Итератор". Наверное.
... << RSDN@Home 1.1.4 beta 5 rev. 395>>
Уйдемте отсюда, Румата! У вас слишком богатые погреба.