
Dmitry
19.09.2017
07:13:59
Для меня Ди очень удобный (можно делать что хочу, как хочу, и это часто будет выглядеть приятно). Широкий спектр от уровня Си и ниже до высокоуровневых высот всяких higher-kinded types. И при этом быстрый. В итоге годится и там, где был нужен С++, и там, где иные пишут на питоне или скале.. Ну и статическая интроспекция (на которой стоит Design by introspection) - это такой наркотик, как освоишь, потом сложно слезть. :)

Dmitry
19.09.2017
07:14:40
мне по части сравнения с Erlang хотелось бы

Dmitry
19.09.2017
07:15:43
А, плюсы Ди по сравнению с Эрлангом. Ща:

Maxim
19.09.2017
07:15:47
можно перефразировать: удобнее, чем Erlang и далее по тексту)

Google

Dmitry
19.09.2017
07:16:31
посмотри как я там про остальные языки написал, нужно что-то в этом духе

Dmitry
19.09.2017
07:20:04
Эрланг все же тормозной. Он интерпретируемый как PHP (хотя есть вариант с JIT компиляцией - HiPE - но его редко в продакшне используют, видимо, не все там гладко). Ди компилируется в нативный код.
Эрланг динамически типизированный. Это плохо и для скорости (неэффективное представление данных), и для моей психики. На динамических языках писать что-то большое - это для особенных людей, я так не могу.
У Ди синтаксис человеческий. Эрланг многое унаследовал от Пролога, все эти запятые с точками это ужос.
Троллинг (но правда) : по умолчанию строка в эрланге это связанный список чисел! Ну как так можно вообще? :)

Dmitry
19.09.2017
07:21:14
строка это число??

Dmitry
19.09.2017
07:21:29
Список из букв, каждая буква - число.
Т.е. на фоне эрланга Ди намного эффективнее представляет данные в памяти, не тратит процессор на интерпретацию байткода, и бережет программиста по части синтаксиса, типизации и удобства в целом. Но по устойчивости к ошибкам и по средствам для распределенных вычислений Ди сосет.

Maxim
19.09.2017
07:25:33

Dmitry
19.09.2017
07:25:53
Однонаправленный, возможно

Maxim
19.09.2017
07:26:11
господа знают толк)
хотя, так подстроки удалять быстрее, чем из массива)

Max
19.09.2017
07:28:27

Dmitry
19.09.2017
07:29:02
В хаскеле так же было, только типизированно все же. Там String = [Char], список Char'ов
Но с тех пор в хаскель завезли еще штук пять разных типов строк.
В эрланге теперь тоже есть более нормальные строки (не списки), но с ними как-то иначе надо обращаться, не как с родными строками.

Google

Dmitry
19.09.2017
07:33:39
хотя, так подстроки удалять быстрее, чем из массива)
Если только из начала. Ведь вырезать середину так просто не выйдет - начало строки это иммутабельный список. Надо построить новый список, где начало будет как у исходной строки, а продолжением будет хвост старой. Использовать начало старой не выйдет.

Maxim
19.09.2017
07:34:08
а да, иммутабельность же

Andrey
19.09.2017
07:36:42
можно я повторюсь с вопросом еще раз, мб, кто что-нибудь подскажет, направление размшлений, так сказать:
Andrey Bukhanovsky, [Sep 19, 2017, 10:11:03 AM]:
пробую разобраться с шаблонами никак не могу понять, почему происходит такая штука:
class cContainerArray{
template container(T){Array!T objects;}
this(){}
void add(T)(T obj){container!(T).objects ~= obj;}
ulong getSize(T)(){return container!(T).objects.length;}
}
cContainerArray cA = new cContainerArray();
cContainerArray cB = new cContainerArray();
cA.add!(object)(obj1);
cB.add!(object)(obj2);
writeln(«cB size is ", cB.getSize!(object)());
получаю результат - «cB size is 2», по идее должно быть 1
то есть obj1 и obj2 попадают в оба массива
переписать-то я переписал этот пример, но все равно получается как-то странно
а вопрос по приведенному примеру - почему все же так получается?


Dmitry
19.09.2017
07:39:31
Тут надо смотреть, куда попадает объявленное внутри template. Видимо, не в поля класса, хоть темплейт и описан внутри класса.
Скорее всего, тут класс лишь namespace обеспечивает
А получается глобальный массив objects

Andrey
19.09.2017
07:41:44
да, какой-то эффект глоабльности (:

Dmitry
19.09.2017
07:41:52
https://github.com/PhilippeSigaud/D-templates-tutorial/blob/master/D-templates-tutorial.pdf

Andrey
19.09.2017
07:42:18
уже все перетрес, переписал вот так:
class cContainerArray(T){
//template container(T){Array!T objects;}
Array!T objects;
this(){}
void add(T obj){objects ~= obj;}
ulong getSize(){return objects.length;}
}
но тогда получается еще забава одна
попробую в словах описать - если я объект такого класса размещаю в другом классе, например, buffer, а потом делаю, например, массив таких буферов, то получается опять =глобальность= - объект, занесенный в objects любого из буферов появляется в каждом таком буфере (:
если просто создавать объект класса cContainerArray, то все нормально

Dmitry
19.09.2017
07:46:22
Тут надо просто не забывать, что class в D это семантически как struct * в С++. Поле-объект это лишь указатель.
10 побитовых копий буфера будут иметь 10 равных указателей на один и тот же объект

Andrey
19.09.2017
07:48:21
я делаю так:
auto _buffs = new cContainerArray!cBuffer;
for (int i = 0; i < _countBuffers; i++){
_buffers ~= new cBuffer();
}

Google

Andrey
19.09.2017
07:48:29
но сути, видимо ,не меняет

Dmitry
19.09.2017
07:50:01
Если целиком пример на gist.github.com или там dpaste положишь, сможем ответить

Andrey
19.09.2017
07:50:31
ок, сегодня постараюсь сделать, спасибо.

Dmitry
19.09.2017
08:07:19
На канале про Раст сформулировали определение низкоуровневости :)

Andrey
19.09.2017
08:43:25
ну вот как-то так. туплю, наверное, попросту. но понять не могу как (:

Dmitry
19.09.2017
08:58:08
https://dpaste.dzfl.pl/0916f0f572d1
_objects = new cContainerArray!cObject надо делать в конструкторе cBuffer
Тогда это выполняется при создании каждого буффера
А то, что было - там один объект создавался в компайл-тайме, и все объекты типа cBuffer имели ссылку на него одного
Когда что-то инициализируем в классе не в конструкторе, а field = value,

Dmitry
19.09.2017
09:00:42
то это значение запоминается в "слепке" для инициализации объектов этого типа

Andrey
19.09.2017
09:01:34
вот оно что. а у меня в начальных версиях было в конструкторе, но по ходу суеты выпало наружу. спасибо большое за объяснение.

Dmitry
19.09.2017
09:04:16
Там интересный эффект - если в конструкторе cContainerArray добавить writeln (как в моем примере), то он не дает напиать _objects = new cContainerArray!cObject за пределами конструктора, т.е. ему надо это значение вычислить в компайл-тайме единожды, а там writeln недоступен.

Andrey
19.09.2017
09:08:03
в общем - читать мне еще кучу всего (:
еще раз спасибо!

Dmitry
21.09.2017
06:36:18
Так, а режим betterC в LDC был доступен? Просто этот ключ вроде бы давно очень был. Что он до этого делал?
Кстати, я по моему спрашивал как место можно резервировать для массива?
Кроме Length вот еще вариант:
string x = [1,2,3,4,5];
x.reserve = 100;
writeln(x.capacity);
только не понятна разница с .length

Google

Dmitry
21.09.2017
07:39:27
https://dlang.org/phobos/object.html#.reserve

NullSanya
21.09.2017
07:40:34

Dmitry
21.09.2017
07:41:39
но length же изменяемое...

NullSanya
21.09.2017
07:43:12
но length же изменяемое...
а foreach Не на length опирается?
просто тогда если зарезервировать много места через length, то много итераций будет

Dmitry
21.09.2017
07:43:54
почему много? по идее наоборот мало.

NullSanya
21.09.2017
07:45:15

Maxim
21.09.2017
07:46:56
reserve устанавливает именно capacity через _d_arraysetcapacity, а length именно длину массива
другими словами, когда выставляется length=100, в массиве _реально появляется 100 элементов_, а при reserve=100 резервируется место под 100 элементов, а длина массива не меняется.

Admin
ERROR: S client not available

Dmitry
21.09.2017
07:49:31
а...
тоесть length лучше для ресайза не использовать т.к. это к ошибкам приведет?

NullSanya
21.09.2017
07:51:23

Maxim
21.09.2017
07:51:50
это приведет к тому, что реальный размер массива поменяется, приведет это к ошибкам или нет, зависит исключительно от программиста)

Dmitry
21.09.2017
07:53:16
угуб спасибо, я проверил. действительно так
А в шарпе массивы так же устроены?
там так же можно их размер менять?
а почему у меня в таск-менеджере ничего не меняется? приложение должно же больше памяти потреблять если зарезирвировано много

Andrey
21.09.2017
08:00:19
GC и так резервирует, попробуй больше резервировать

NullSanya
21.09.2017
08:00:29

Dmitry
21.09.2017
08:01:13
я пробовал:
x.reserve = 10_000_000;

Google

NullSanya
21.09.2017
08:01:33

Dmitry
21.09.2017
08:01:42
int[] x = [1,2,3,4,5];

NullSanya
21.09.2017
08:02:28
ну такое кол-во должно быть заметно

Dmitry
21.09.2017
09:25:33
Небольшой вопрос по Горутинам. Те как понимаю вшиты в язык, а тут получается каждая функция должна сама yield вызывать если она хочет работать подобным образом?

Dmitry
21.09.2017
09:25:34
B task manager'e разные стобцы есть. Есть commit - сколько запрошено, а есть working set - сколько реально используется...
Да компилятор go по сути сам расставляет yieldы по коду.

Dmitry
21.09.2017
09:26:56
На винде таких столбцов не вижу
тоесть аналог го-рутины будет:
foo ()
{
// что-то делаем
yield();
}
так?

Andrey
21.09.2017
09:45:15
вроде так. в го переключение гоуротины происходит на блокирующем вызове. хотя может и не так)

Dmitry
21.09.2017
10:42:53
На блокирующих вызовах и внутри циклов еще

Dmitry
21.09.2017
10:44:19
спасибо
а она где выделяется? Типа ОС знает что там нули?

Dmitry
21.09.2017
10:52:07
Программа говорит системе: дай гигабайтик. Система у себя виртуальную память размечает, что такие-то адреса данного процесса теперь ему принадлежат и там нолики. При первом реальном обращении к тем страницам они уже маппятся на страницы физической памяти (которые уже в working set входят). Пока страница выделена, но не использовалась, физическая память не расходуется.

Dmitry
22.09.2017
05:26:37
Как по ассемблерному листингу понять какие данные в стек, а какие в кучу кладутся?
https://d.godbolt.org/
push/pop это стек? Или есть еще какие-то моменты?

Maxim
22.09.2017
05:30:43
по идее, все, что работает с SP/ESP/RSP — это работа со стеком
это если мы говорим про архитектуру x86Ю конечно)

Dmitry
22.09.2017
05:34:13
Я что-то не пойму а где тут число 7 в листинге:

Maxim
22.09.2017
05:35:50
подозреваю, нигде)