Как оформляются связи между immutable-данными?
использовать публичные свойства с приватными сеттерами вместо readonly полей не подойдёт?
Хочется оставаться в рамках парадигмы неизменяемости данных, т.к. это дает кучу полезных плюшек.
А окасаки ты уже читал?
2.
3. Для построения коллекции иногда пользутся изменяемыми билдерами, как в случае со StringBuilder
А окасаки ты уже читал?да, но там про эффективность простых коллекций.
а здесь получается иерархический неоднородный граф
ps
>> 1. МС выпустила библиотеку с коллекцией разных неизменяемых структур данных. Посмотри её в NuGet. System Collections Immutable
спасибо, посмотрю
>> 2. Mans -> Men
неудобно при машинной обработке кода
Хочется оставаться в рамках парадигмы неизменяемости данных, т.к. это дает кучу полезных плюшек.Ты эту парадигму уже нарушил - у тебя связи изменяемые, со всеми вытекающими.
Какие есть паттерны для оформления связей при использовании immutable-данных?Observer, COW, Proxy
А окасаки ты уже читал?я вот не читал, неужели там нет описания реализаций? а все так нахваливают..что же там тогда интересного?
да, но там про эффективность простых коллекций.
Ты эту парадигму уже нарушил - у тебя связи изменяемые, со всеми вытекающими.в смысле?
я вот не читал, неужели там нет описания реализаций? а все так нахваливают..что же там тогда интересного?Он хорош тем, что там детально разбирается эффективность коллекций. В частности, как сделать так, чтобы изменения коллекций были за O(1)
Observer, COW, Proxyкстати, разбор этих паттернов для immutable где можно посмотреть?
COWэто что такое?
COWhttp://en.wikipedia.org/wiki/Copy-on-write
это что такое?
как обходится проблема, что для immutable-данных при обновления элемента необходимо обновить все ссылкиэто делается путем обхода гетерогенной структуры и иммутабельной модификацией каждой составляющей
наиболее красиво это видно на примере хаскела
можно начать отсюда: http://hackage.haskell.org/package/base-4.4.1.0/docs/Data-T...
это делается путем обхода гетерогенной структуры и иммутабельной модификацией каждой составляющейспасибо. Меня как раз интересовало, как это обычно решается в ФЯ.
internal class Program
{
private static void Main(string[] args)
{
var маша = new Man(3, "Маша", 1);
var world = ПоменятьНачальникаУВаси(
new World(
вася: new Man(1, "Вася", 2
петя: new Man(2, "Петя", null
маша: маша
маша);
var men = world.Men.ToDictionary(_ => _.Id);
foreach (var man in world.Men)
{
Console.WriteLine("{0} - {1}",
man.Name, man.ChiefId.HasValue ? men[man.ChiefId.Value].Name : "");
}
}
static World ПоменятьНачальникаУВаси(World world, Man chief)
{
return new World(
вася: new Man(world.Вася.Id, world.Вася.Name, chief.Id
петя: world.Петя,
маша: world.Маша);
}
}
class Man
{
public readonly int Id;
public readonly string Name;
public readonly int? ChiefId;
public Man(int id, string name, int? chiefId)
{
Id = id;
Name = name;
ChiefId = chiefId;
}
}
class World
{
public readonly Man Вася;
public readonly Man Петя;
public readonly Man Маша;
public World(Man вася, Man петя, Man маша)
{
Вася = вася;
Петя = петя;
Маша = маша;
}
public IEnumerable<Man> Men
{
get
{
yield return Вася;
yield return Петя;
yield return Маша;
}
}
}
наиболее красиво это видно на примере хаскелая про хаскель почти ничего не знаю, но не вижу в примере, как сделать чтоб не обходить всё дерево, а только те узлы, которые меняются?
я про хаскель почти ничего не знаю, но не вижу в примере, как сделать чтоб не обходить всё дерево, а только те узлы, которые меняются?Что такое "обходить только те узлы, которые меняются"?
ps
Корень проблемы изменения сложных данных с перекрестными ссылками как раз в том, что сложно предсказать какая часть дерева будет затронута при изменении одного элемента.
отложить обход до того момента, как он понадобится. Отложить ещё больше, используя линзы. Надеяться на амортизированную сложность.
Что такое "обходить только те узлы, которые меняются"?ну там в примере я так понял предлагают запустить некий вариант map который поменяет все узлы
а у тебя задача: один узел меняется, надо побыстрее найти только те, которые на него ссылаются (ну и далее до корня)
сейчас кстати в моде файловые системы, которые примерно так устроены, вроде btrfs
а у тебя задача: один узел меняется, надо побыстрее найти только те, которые на него ссылаются (ну и далее до корня)нет других общих красивых решений, кроме fullscan-а
ps
"Некрасивые" решения - усложняют операцию создания дерева.
Чтобы менять точечно, элемент должен хранить "ссылки" на все ссылки, которые на него ссылаются. "Ссылки" должны быть в формате пути. Путь - это способ перейти от корня к элементу (прямой путь) или от элемента к корню(обратный путь).
Подвох в том, что пути меняются при операции композиции дерева: соответственно, операция композиции резко усложняется: требуя перестраивания путей, а не просто конкатенации двух элементов.
Если использовать обратные пути (через ссылку на родителя тогда операция конкатенации так же усложняется, т.к. если элемент вставляется во второе место дерева, то необходимо делать полную копию такого элемента (т.к у всех подэлементов меняются родители что убивает всю прелесть immutable.
Насколько я помню на хаскел так и не вышло строить суффиксальное дерево за линейное время, если только не закамуфлировать императивный алгоритм и прямой доступ к памяти в монаду. Лучший алгоритм имеет скорость O(n*log(n такую же асимптоту можно легко получить из традиционного метода, заменив доступ по ссылкам O(1) на поиск по ключу O(log(n
т.к. если элемент вставляется во второе место дерева, то необходимо делать полную копию такого элементазачем копию? несколько ссылок храни
зачем копию? несколько ссылок храниИнтересная идея! Для смыслового применения множественные родительские ссылки вводят путаницу, а вот для служебного использования вполне подходят.
задачи навскидку те же, и уменьшение количества копирований очень важно
и код пишут настоящие мужики на суровом си, а не на каком-то гейском хаскеле
ну не знаю поможет ли, но посмотри на btrfsспасибо, посмотрю.
Оставить комментарий
Dasar
Какие есть паттерны для оформления связей при использовании immutable-данных?Интересует, как обходится проблема, что для immutable-данных при обновления элемента необходимо обновить все ссылки, которые на этот элемент ссылаются.
пример