The OpenNET Project / Index page

[ новости /+++ | форум | теги | ]



Вариант для распечатки  
Пред. тема | След. тема 
Форум Разговоры, обсуждение новостей
Режим отображения отдельной подветви беседы [ Отслеживать ]

Оглавление

Релиз языка программирования Go 1.8, opennews (??), 17-Фев-17, (0) [смотреть все]

Сообщения [Сортировка по времени | RSS]


55. "Релиз языка программирования Go 1.8"  –3 +/
Сообщение от Аноним (-), 17-Фев-17, 15:11 
Никогда не понимал, зачем нужен сборщик мусора? В С++ его нет, и никаких проблем это не создаёт.
Ответить | Правка | Наверх | Cообщить модератору

65. "Релиз языка программирования Go 1.8"  +9 +/
Сообщение от Аноним (-), 17-Фев-17, 15:29 
> Никогда не понимал, зачем нужен сборщик мусора? В С++ его нет, и
> никаких проблем это не создаёт.

Совершенно никаких, даром что USE-AFTER-FREE входит в 20ку самых эксплуатируемых уязвимостей. Примерчик с пылу с жару:
CVE-2016-7117 - критическая дыра в ядре Linux Рейтинг опасности 10/10


Ответить | Правка | Наверх | Cообщить модератору

68. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 15:35 
Мне кажется люди просто не знаю, что уже давно проблема ручного контроля освобождения памяти решена std::unique_ptr. Все до сих пор считают что там, где нет сборщика мусора, надо писать что-то вроде:

> TYPE n = new TYPE()
> .....
> // много кода
> delete n;

Но нет, объект удаляется автоматически, и тогда, когда это нужно программисту, а не когда соизволит сборщик.

Ответить | Правка | Наверх | Cообщить модератору

73. "Релиз языка программирования Go 1.8"  +3 +/
Сообщение от Василий Теркин (?), 17-Фев-17, 15:45 
> Мне кажется люди просто не знаю, что уже давно проблема ручного контроля
> освобождения памяти решена std::unique_ptr. Все до сих пор считают что там,
> где нет сборщика мусора, надо писать что-то вроде:
>> TYPE n = new TYPE()
>> .....
>> // много кода
>> delete n;
> Но нет, объект удаляется автоматически, и тогда, когда это нужно программисту, а
> не когда соизволит сборщик.

Ну да, ну да... Когда НУЖНО программисту. Только страдают от этого потом пользователи и системы. Ведь программист, в силу своего эгоцентризма, даже не подозревает, что задачки, выполняемые его кодом, могут быть не самыми приоритетными в системе. Или программеры уже научились предугадывать в каком "обвесе" будет работать их код в будущем? В свое время для этого и придумали API, чтобы юные вундеркинды не крашили систему прямым управлением аппаратными ресурсами.

Ответить | Правка | Наверх | Cообщить модератору

77. "Релиз языка программирования Go 1.8"  –4 +/
Сообщение от Аноним (-), 17-Фев-17, 15:55 
Сборщик мусора не удалит объект, пока на него есть ссылки. И запускается он через определенные промежутки времени. Т.ч. в языке со сборщиком мусора объекты могут жить дольше, но не меньше. И при этом дольше - это обычно во много раз дольше. В с++ даже локальный объект можно удалить автоматически до выхода из функции просто ограничив ему область видимости фигурными скобками. В том же Go он будет жить еще несколько мс после завершения функции, пока сборщик не соизволит пошевелиться.
Ответить | Правка | Наверх | Cообщить модератору

86. "Релиз языка программирования Go 1.8"  +7 +/
Сообщение от Аноним (-), 17-Фев-17, 16:10 
> Сборщик мусора не удалит объект, пока на него есть ссылки. И запускается
> он через определенные промежутки времени.

Фееричные-познания-в-теме-рука-лицо.жпг

> В с++ даже локальный
> объект можно удалить автоматически до выхода из функции просто ограничив ему
> область видимости фигурными скобками. В том же Go он будет жить
> еще несколько мс после завершения функции, пока сборщик не соизволит пошевелиться.

Опять тайные знания? На самом деле есть только один GC, а еscape анализ придумка маркетологов?


Ответить | Правка | Наверх | Cообщить модератору

121. "Релиз языка программирования Go 1.8"  –2 +/
Сообщение от Аноним (-), 17-Фев-17, 17:52 
Ветка про сборщик мусора, а не про Go. Везде разные реализации сборщика.
Ответить | Правка | Наверх | Cообщить модератору

133. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 17-Фев-17, 18:01 
> Ветка про сборщик мусора, а не про Go.

Ответ как раз про _сборщики_ мусора, а не специфику го.
> Везде разные реализации сборщика.

Алгоритмов сборки целая куча. И работают они очень по разному.
И да, упоминание "а вот так можно в плюсах" тоже не в тему - это особенность конретного ЯП.


Ответить | Правка | Наверх | Cообщить модератору

90. "Релиз языка программирования Go 1.8"  +2 +/
Сообщение от Аноним (-), 17-Фев-17, 16:23 
> В том же Go он будет жить еще несколько мс после завершения функции, пока сборщик не соизволит пошевелиться.

Go использует стандартную реализацию стека. Все локальные переменные будут удалены* мгновенно при возврате из функции, аналогично с/с++.

*Указатель на стек вернется в состояние до вызова функции.

Ответить | Правка | К родителю #77 | Наверх | Cообщить модератору

97. "Релиз языка программирования Go 1.8"  +/
Сообщение от hoopoeemail (ok), 17-Фев-17, 16:47 
там же замыкания на уровне языка реализованы... как их на стек положить?
Ответить | Правка | Наверх | Cообщить модератору

125. "Релиз языка программирования Go 1.8"  +2 +/
Сообщение от Мяут (ok), 17-Фев-17, 17:55 
Там компилятор автоматически определяет, нужно ли переменную на стеке создавать (если она не покидает пределов области видимости) или в куче. Можно -gcflags -m использовать, оно скажет что будет на куче создаваться. Например:


type S struct {
    I int
}

func foo() func () S {
    var s S
    fmt.Scan(s.I)
    return func () S { return s }
}

скажет "src/stack.go:13: s.I escapes to heap"

UPD: благодаря этому можно кстати поинтеры на локальные переменные возвращать без плохих последствий

Ответить | Правка | Наверх | Cообщить модератору

172. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 21:11 
Еще зависит от размера и типа переменной и от самой функции, как она вызывается. Стек не резиновый...
Ответить | Правка | Наверх | Cообщить модератору

123. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 17-Фев-17, 17:53 
В общем случае да, но есть исключения
Ответить | Правка | К родителю #90 | Наверх | Cообщить модератору

78. "Релиз языка программирования Go 1.8"  –2 +/
Сообщение от Аноним (-), 17-Фев-17, 15:56 
Системы с ограниченными ресурсами самое то, чтобы распылять их на потуги сборщика и висящие неиспользуемые объекты, которые он непонятно когда удалит.
Ответить | Правка | К родителю #73 | Наверх | Cообщить модератору

87. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 17-Фев-17, 16:12 
У вас в квартире дверь есть?
Ответить | Правка | Наверх | Cообщить модератору

120. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 17:50 
У вас в квартире унитаз есть?
Ответить | Правка | Наверх | Cообщить модератору

132. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 18:00 
В магазине:

- У вас трусы есть?
- Нет.
- А в продаже?

Ответить | Правка | Наверх | Cообщить модератору

156. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Аноним (-), 17-Фев-17, 18:48 
На автоматическое управление памятью тратятся вычислительные ресурсы машины.
На ручное управление памятью тратятся временные ресурсы программиста.

Говорить о том, какой выбор оптимальнее можно только в конкретных случаях. Например, если использовать ручное управление памятью и потерять на это месяц работы, мы заработаем примерно $10000, а если направим время программистов на написание фичи X, то заработаем примерно $15000, 15000 > 10000 -> нет смысла тратить время на ручное управление памятью.

Ответить | Правка | К родителю #78 | Наверх | Cообщить модератору

173. "Релиз языка программирования Go 1.8"  –2 +/
Сообщение от Аноним (-), 17-Фев-17, 21:14 
Написали уже, оптимальный - умные указатели. Никакого тебе сборщика мусора и ручного освобождения памяти. Месяц вы никак не потеряете, обернуть вызов new в умный указатель - пара секунд.
> TYPE *p = new TYPE();

в
> std::unique_ptr<TYPE> p(new TYPE());

И всё.

Ответить | Правка | Наверх | Cообщить модератору

80. "Релиз языка программирования Go 1.8"  –3 +/
Сообщение от Аноним (-), 17-Фев-17, 15:57 
Краши уже в прошлом, есть статические анализароры, умные указатели, диапазонные циклы и т.д.
Ответить | Правка | К родителю #73 | Наверх | Cообщить модератору

88. "Релиз языка программирования Go 1.8"  +/
Сообщение от Василий Теркин (?), 17-Фев-17, 16:13 
> Краши уже в прошлом, есть статические анализароры, умные указатели, диапазонные циклы и
> т.д.

Вы серьезно?

Ответить | Правка | Наверх | Cообщить модератору

124. "Релиз языка программирования Go 1.8"  –2 +/
Сообщение от Аноним (-), 17-Фев-17, 17:55 
Для меня да. Ваш уровень знания языка вероятно гораздо ниже, раз краши для вас обыденность.
Ответить | Правка | Наверх | Cообщить модератору

140. "Релиз языка программирования Go 1.8"  +2 +/
Сообщение от Василий Теркин (?), 17-Фев-17, 18:12 
> Для меня да. Ваш уровень знания языка вероятно гораздо ниже, раз краши
> для вас обыденность.

А что написали? Судя по приводимым в этой ветке примерам - код из популярной серии "С++ для чайников за 7 дней".

Ответить | Правка | Наверх | Cообщить модератору

94. "Релиз языка программирования Go 1.8"  +2 +/
Сообщение от Orduemail (ok), 17-Фев-17, 16:30 
> Мне кажется люди просто не знаю, что уже давно проблема ручного контроля
> освобождения памяти решена std::unique_ptr. Все до сих пор считают что там,
> где нет сборщика мусора, надо писать что-то вроде:
>> TYPE n = new TYPE()
>> .....
>> // много кода
>> delete n;
> Но нет, объект удаляется автоматически, и тогда, когда это нужно программисту, а
> не когда соизволит сборщик.

Если бы всё было так просто, то мемликов бы не было. Вообще нигде не было бы, даже в ассемблере. Иногда хочется иметь ссылку на объект в разных стековых фреймах, а иногда ещё и в структурке хранить её удобно. А ещё иногда объект прямо или косвенно ссылается сам на себя, тогда даже ref_count не всегда спасает.

Ответить | Правка | К родителю #68 | Наверх | Cообщить модератору

108. "Релиз языка программирования Go 1.8"  –3 +/
Сообщение от Аноним (-), 17-Фев-17, 17:35 
> Если бы всё было так просто, то мемликов бы не было.

А не всё так просто. Но и не всё так ужасно.


> Вообще нигде не было бы, даже в ассемблере.

Как это? В ассемблере же ни смарт-пойнтеров, ни сборщика мусора нет. Наверное какая-то глубокая философия была.


> Иногда хочется иметь ссылку на объект в разных стековых фреймах, а иногда ещё и в структурке хранить её удобно.

"В структурке"? Сишника в вас ощущаю я.

В С++ есть решение из коробки, std::shared_ptr. Помогает в большинстве случаев.

Понятно, что можно извратиться и его обмануть. Но тогда можно и своё решение для этой категории изврата написать.


> А ещё иногда объект прямо или косвенно ссылается сам на себя, тогда даже ref_count не всегда спасает.

В этом случае и сборщик мусора не всегда спасает.

Вот вам хорошая презенташка про утечки памяти в Java:

http://www.slideshare.net/RafaelWinterhalter/a-topology-of-m...

Ответить | Правка | Наверх | Cообщить модератору

158. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Orduemail (ok), 17-Фев-17, 18:51 
>> Вообще нигде не было бы, даже в ассемблере.
> Как это? В ассемблере же ни смарт-пойнтеров, ни сборщика мусора нет. Наверное
> какая-то глубокая философия была.

Потому что до тех пор, пока у нас есть указатель вписывающийся в идею uniq_ptr, отследить время жизни объекта не просто, а крайне просто. Я не знаю кем надо быть, чтобы забыть его удалить.

>> Иногда хочется иметь ссылку на объект в разных стековых фреймах, а иногда ещё и в структурке хранить её удобно.
> "В структурке"? Сишника в вас ощущаю я.

Пфеу.

> В С++ есть решение из коробки, std::shared_ptr. Помогает в большинстве случаев.

Угу. Да, подсчёт ссылок решает большинство таких проблем, я о том и говорю. Но не все. Я когда-то читал у Кнута, что подсчётом ссылок можно решать на системном уровне даже работу с циклическими объектами, но с тех пор так и не собрался походить по ссылкам и выяснить -- не врал ли он.

>> А ещё иногда объект прямо или косвенно ссылается сам на себя, тогда даже ref_count не всегда спасает.
> В этом случае и сборщик мусора не всегда спасает.

В этом случае спасает. Даже консервативный сборщик мусора одетый на C++ сможет эту проблему вычленить и освободить память. Правда он консервативный -- он не имеет информации о типах переменных, и поэтому если какой-нибудь буфер, куда был прочитан файл, содержит значение похожее на указатель в потерянный объект, то он сохранит этот объект на всякий случай.

> Вот вам хорошая презенташка про утечки памяти в Java:
> http://www.slideshare.net/RafaelWinterhalter/a-topology-of-m...

Ой, ну естественно. Если ты подключаешь к программе со сборкой мусора библиотеки без сборки мусора, то их объекты сборщик мусора не может тупо удалять, потому что он не может проверить unsafe код на предмет владения указателями. Если ты начинаешь использовать unsafe код, то половина гарантий, которые даёт язык просто отваливаются, и там всё упирается в то, способен ли ты управлять памятью вручную.
Это проблемы не сборщика мусора, как такового -- это проблемы вылезающие из-за неиспользования сборщика мусора кодом.

Ответить | Правка | Наверх | Cообщить модератору

165. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 19:31 
> Потому что до тех пор, пока у нас есть указатель вписывающийся в идею uniq_ptr, отследить время жизни объекта не просто, а крайне просто. Я не знаю кем надо быть, чтобы забыть его удалить.

Не всегда просто. Легко забыть сделать delete перед return в середине функции. Особенно если указателей несколько, return-ов тоже несколько, и надо перед разными return надо делать разный набор delete. Также вместо преждевременного return бывает исключение, да ещё в какой-нибудь вложенной функции.


> Пфеу.

Принято. :)


> Да, подсчёт ссылок решает большинство таких проблем, я о том и говорю.  Но не все.

Так и GC не все. Да, теоретически GC может освободить больше памяти, чем RAII. А практически - оба подхода работают очень хорошо. А RAII может ещё и другие ресурсы автоматически освобождать, например закрывать файлы, сетевые соединения, БД-соединения и т.д.


> В этом случае спасает.

Циклические ссылки циклическим ссылкам рознь. Не всегда GC может их правильно раскрутить.


> unsafe код

Посмотрите презентацию повнимательнее, дальше 7-й страницы. Так не только unsafe код.

Ответить | Правка | Наверх | Cообщить модератору

168. "Релиз языка программирования Go 1.8"  +3 +/
Сообщение от Orduemail (ok), 17-Фев-17, 20:10 
>> Потому что до тех пор, пока у нас есть указатель вписывающийся в идею uniq_ptr, отследить время жизни объекта не просто, а крайне просто. Я не знаю кем надо быть, чтобы забыть его удалить.
> Не всегда просто. Легко забыть сделать delete перед return в середине функции.
> Особенно если указателей несколько, return-ов тоже несколько, и надо перед разными
> return надо делать разный набор delete. Также вместо преждевременного return бывает
> исключение, да ещё в какой-нибудь вложенной функции.

Вот нефиг писать исключительно на C++. Попробуй пописать на C или asm годик, тебе в кровь въестся идея, что return из середины функции -- это плохо, и прежде чем так делать, нужно три раза подумать. ;)
Это реально выходит на уровень условного рефлекса, который срабатывает всегда, при виде return, за которым тело функции продолжается. Даже если писать приходится на питоне -- всё равно срабатывает. Так и хочется вместо return написать goto finish.
Или, если на C/asm аллергия, то вместо них можно попробовать какую-нибудь функциональщину, в которой вообще использование return -- признак дурного тона, а для cleanup кода, если он нужен, есть какой-нибудь особый костыль, позволяющий обходиться без return и без создания временной переменной для хранения результата вычислений, пока выполняется этот самый cleanup код. Что-нибудь типа unwind-protect в common lisp'е.

>> Да, подсчёт ссылок решает большинство таких проблем, я о том и говорю.  Но не все.
> Так и GC не все. Да, теоретически GC может освободить больше памяти,
> чем RAII. А практически - оба подхода работают очень хорошо. А
> RAII может ещё и другие ресурсы автоматически освобождать, например закрывать файлы,
> сетевые соединения, БД-соединения и т.д.

Я в последний раз сталкивался с жабой лет пятнадцать назад, но даже тогда она умела закрывать файловые дескрипторы, когда умирали объекты, владеющие ими. Там было что-то типа метода finalize -- деструктор, который вызывался непосредственно перед освобождением памяти. Это было дерьмово, потому что пока сборщик мусора не выяснит, что объект умер, он не вызовет finalize, а finalize не вызовет close(2) и файловый дескриптор будет оставаться открытым, что неудачно, если много файловых дескрипторов открывается и закрывается. Поэтому всё равно, стоило закрывать файлы прежде чем терять ссылки на них. Но это было даже тогда. Ну, чтобы это работало, конечно же, надо избегать работать с файловым дескриптором напрямую и работать с ним исключительно через посредство специально созданного объекта со специально заточенным finalize.

>> В этом случае спасает.
> Циклические ссылки циклическим ссылкам рознь. Не всегда GC может их правильно раскрутить.

Если циклическая ссылка недоступна из корневого указателя, то gc её даже не найдёт, потому что он ищет не объекты, которые нужно удалять, а объекты, которые нужно сохранять. Может речь про вызов деструкторов циклического объекта? Там, вероятно, могут возникать проблемы -- если у нас есть цикл из однотипных объектов, то чей деструктор вызывать первым? М-м-м... Я не думал об этом. Может просто вызвать их в рандомном порядке? Какая собственно разница.

>> unsafe код
> Посмотрите презентацию повнимательнее, дальше 7-й страницы. Так не только unsafe код.

Я не умею смотреть презентации, я их не понимаю -- какие-то случайным образом раскиданные по слайду непонятные схемки и буковки... Можно мне сам доклад текстом, а не только картинки из него?

Ответить | Правка | Наверх | Cообщить модератору

175. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 21:21 
> return из середины функции -- это плохо

Может так и есть, но ведь так удобно! :) Выяснил, что больше делать нечего, и до свиданья. И, продолжая минутку юмора, если не делать ранних return-ов, может получиться вот так: https://pbs.twimg.com/media/Bp1IyS7CYAATIEB.jpg :)


> finalize -- деструктор ... дерьмово

Да, вот я про это самое.


> пока сборщик мусора не выяснит, что объект умер, он не вызовет finalize

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


> лет пятнадцать назад

С тех пор (а может и тогда было) придумали finally и try-with-resources, что, в общем-то, неплохо. В отличие от деструктора, работает только в одном scope.


> Можно мне сам доклад текстом

Поискал специально для тебя, не нашёл. :( Хотя доклад очень хороший был.

Нашёл другое:

The different kinds of Java memory leaks and how to analyze them
https://www.dynatrace.com/resources/ebooks/javabook/memory-l.../
Один из разделов, кстати, называется "Circular and Complex Bi-Directional References".

Ну и на гугле, и на ютубе тоже, на эту тему много.

Ответить | Правка | Наверх | Cообщить модератору

178. "Релиз языка программирования Go 1.8"  +/
Сообщение от Orduemail (ok), 17-Фев-17, 22:17 
>> return из середины функции -- это плохо
> Может так и есть, но ведь так удобно! :) Выяснил, что больше
> делать нечего, и до свиданья.

Ну, много чего есть удобного, что потом может выйти боком. Для этого и придумывают всякие CodingStyle, чтобы ограничить программиста в том, какие глупости он может совершить.

> И, продолжая минутку юмора, если не
> делать ранних return-ов, может получиться вот так: https://pbs.twimg.com/media/Bp1IyS7CYAATIEB.jpg
> :)

:)
Да, я сталкивался с таким. Причём в C коде. Причём авторства IBM. Но там было хуже, там вперемешку десятками вкладывались if, for, while... И отступы по два пробела. Здесь-то однотипные проверки, которые можно раскидать по функциям и вызывать их в цикле, а можно и ничего не делать -- и так в общем-то понятно что происходит. Но в том драйвере флоповода был просто вынос мозга. Причём не в одном каком-то месте, а постоянно.

> Нашёл другое:
> The different kinds of Java memory leaks and how to analyze them
> https://www.dynatrace.com/resources/ebooks/javabook/memory-l.../

Спасибо.

> Один из разделов, кстати, называется "Circular and Complex Bi-Directional References".

Там не memleak. Или, если очень хочется, то memleak, но не в строгом понимании этого слова -- всё совершенно законно. Если мы храним Node, а Node зачем-то хранит Document, то память доступна приложению. Удаление нода приведёт к удалению Document. То есть это наверное неудобно для кодера -- ему надо для отлавливания таких штук понимать, как работает API, которым он пользуется, но я не вижу что с этим можно сделать, со сборщиком мусора или без него. Хотя... lifetimes и borrowing позволяют творить чудеса... может и можно спроектировать API так, чтобы если не решить проблему вообще, то хотя бы ограничить её рамками lifetime'а переменной, хранящей Document. Может быть даже удастся обойтись без сборки мусора (и без gc, и без счётчика ссылок) для последующего освобождения памяти Node.
Но, соглашусь, lifetime/borrowing это уже не GC, а другой способ решения проблемы.

> Ну и на гугле, и на ютубе тоже, на эту тему много.

Ну, мне на самом деле не очень интересно -- интересно, но не настолько, чтобы я погрузился бы в поиски: я не думаю, что вдруг я найду, что-то новое. Если бы я писал на жабе или го, то пошёл бы и поискал, но я не пишу на них.

Ответить | Правка | Наверх | Cообщить модератору

184. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от анонимчик (?), 17-Фев-17, 23:23 
>В С++ есть решение из коробки, std::shared_ptr. Помогает в большинстве случаев.

который на каждый чих мьютекс блокирует.. проще на питоне написать и слипы повставлять.

Ответить | Правка | К родителю #108 | Наверх | Cообщить модератору

128. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 17:56 
Во всех этих случаях требуется пересмотр архитектуры приложения.
Ответить | Правка | К родителю #94 | Наверх | Cообщить модератору

164. "Релиз языка программирования Go 1.8"  +3 +/
Сообщение от Orduemail (ok), 17-Фев-17, 19:26 
> Во всех этих случаях требуется пересмотр архитектуры приложения.

Требуется. И что? Ну пересмотришь ты её, а дальше что? Будешь переписывать пару сотен тысяч строк кода? Или ты до сих пор веришь в миф 90-х годов о том, что программу можно спроектировать заранее так, чтобы потом не возникало проблем с архитектурой?

Ответить | Правка | Наверх | Cообщить модератору

182. "Релиз языка программирования Go 1.8"  –2 +/
Сообщение от Аноним (-), 17-Фев-17, 23:06 
> Или ты до сих пор веришь в миф 90-х годов о том, что программу можно
> спроектировать заранее так, чтобы потом не возникало проблем с архитектурой?

Это "стало мифом", когда стало модно быть балбесом.

Ответить | Правка | Наверх | Cообщить модератору

185. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Orduemail (ok), 18-Фев-17, 00:03 
Может быть.

Но я склонен разделять мнение этих 95%, которые считают, что проблема в возросшей сложности софта. Пару месяцев назад я читал статейку -- ребята провели исследования нескольких крупных проектов, на предмет взаимосвязей между различными частями кода, причём как-то они этот код разбивали по уровням примерно так (сейчас я навру скорее всего, потому что не помню, но сочиняю): минимальное деление -- код разбивается на функции, среднее -- на файлы, крупное ещё как-то. И просто посчитали количество ссылок по горизонтали -- между частями одного уровня, и по вертикали, между частями разных уровней. Цель была оценить качество кода -- чем меньше взаимосвязей, тем лучше проектирование.
Так вот, там большинство проектов или даже все на низком уровне показывали весьма пристойный уровень проектирования, на среднем было ~50/50, а на верхнем у всех получался бардак, безумная мешанина из связей между различными частями. Вывод напрашивается очевидный: человек просто не способен проектировать системы подобной сложности. И если осталость в мире 5% уникумов, которые могут, то, во-первых, найти их не удастся ни мне, ни тебе, а во-вторых, это не надолго: пройдёт ещё пять лет, и эти 5% тоже сломаются под всё возрастающей сложностью софта.

Там, правда, выборка была небольшая -- меньше десяти проектов, но там были проекты на C, на C++, Java -- это я точно помню. И вывод этот очень хорошо укладывается в общую картину. Я, к сожалению, ссылку не могу найти, чтобы ты сам мог бы посмотреть в деталях.

Ответить | Правка | Наверх | Cообщить модератору

190. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Аноним (-), 18-Фев-17, 08:39 
KISS.
Ответить | Правка | Наверх | Cообщить модератору

198. "Релиз языка программирования Go 1.8"  +2 +/
Сообщение от chinarulezzz (ok), 18-Фев-17, 16:20 
Потому что, если не вся, то большая часть _сложности_ вытекает из 1) незнания: хождения вслепую, велосипедов с квадратными колёсами, антипаттернов, спагетти-кода, и т.п. 2) экономики: комбайны, обфускация и усложнение исследования кода для конкурентного преимущества и т.п.

Всё гениальное -- просто, KISS не выгоден ввиду сложившейся системы:

#Комбайнёры, комбайнёры ©
#I want to ride my bicycle ©

Ответить | Правка | Наверх | Cообщить модератору

118. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 17-Фев-17, 17:49 
Нет, не решена. Программист должен изначально знать нужен ему unique_ptr или shared_ptr, а может weak_ptr?
В языках с GC об этом можно просто не думать, там везде shared_ptr.
Это ещё не говоря о том, насколько замусоривается код:
fun() -> std::unique_ptr<std::array<std::shared_ptr<Node>>>;
Ответить | Правка | К родителю #68 | Наверх | Cообщить модератору

131. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 18:00 
shared_ptr, а уж тем более weak_ptr - это вообще наиредчашие случаи. Я за 15 лет программирования shared_ptr использовал только один раз.
А код замусоривается потому что неправильно пишете.
Вот это вот:
> std::unique_ptr<std::array<std::shared_ptr<Node>>>

очевидно неправильная конструкция, надо разбираться, почему такая х получилась.

Ответить | Правка | Наверх | Cообщить модератору

149. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Аноним (-), 17-Фев-17, 18:25 
Не думаю, что редчайшим случаем является ситуация, когда неизвестно кто из владельцев должен уничтожить объект.

А ещё, по хорошему, нужна невладеющая обёртка поинтера, см observer_ptr.
Итого программист выбирает между хранением и передачей по значению, голому указателю, уникальному указателю, разделяемому указателю, weak указателю, observer_ptr, ссылке, std::reference_wrapper (враппер ссылки). Хороший язык, ничего не скажешь, есть инструменты на все случаи жизни. Только кто в этом разбираться будет? Семантика копирования, семантика перемещения..

Подскажите, как правильно, пожалуйста. Потому что в моём коде такое часто встречается. Использую алиасы типов.

using BucketType = std::vector<NodeInfo>;
using Bucket = std::unique_ptr<BucketType>;
using Buckets = std::array<Bucket, Parameters::B>;

Ответить | Правка | Наверх | Cообщить модератору

177. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 21:43 
> Не думаю, что редчайшим случаем является ситуация, когда неизвестно кто из владельцев должен уничтожить объект.

Ситцация, когда нужен shared_ptr? Такая ситуация является просто очень редкой. По сравнению с unique_ptr.

А редчайший случай (хоть и не невозможный) - это когда кажется, что хватит и unique_ptr, а потом оказывается, что не хватает, и нужен shared_ptr.


> Подскажите, как правильно, пожалуйста. Потому что в моём коде такое часто встречается. Использую алиасы типов.
> using BucketType = std::vector<NodeInfo>;

Пойдёт как syntax sugar.

> using Bucket = std::unique_ptr<BucketType>;

Не нужно, вектор и так в куче выделяет. Разве что хочется гарантировать уникальность (некопирование).

> using Buckets = std::array<Bucket, Parameters::B>;

Двумерный массив типа? Можно так, можно вектор векторов.

Ответить | Правка | Наверх | Cообщить модератору

189. "Релиз языка программирования Go 1.8"  +/
Сообщение от Андрей (??), 18-Фев-17, 07:25 
> Но нет, объект удаляется автоматически, и тогда, когда это нужно программисту, а не когда соизволит сборщик.

А что с динамическим выделением объекта? Он-то выделится тогда, когда это нужно программисту, но от этого не легче, так как алгоритм выделения в куче не ограничен константным временем. А всё дело во времени: не хочется иметь непредвиденных задержек. Так вот с GC они и так уже небольшие, а что с выделением в куче?

Ответить | Правка | К родителю #68 | Наверх | Cообщить модератору

200. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 18-Фев-17, 17:49 
Какой аллокатор напишешь - так и будет выделяться. А GC никогда не был и не будет предсказуем.
Ответить | Правка | Наверх | Cообщить модератору

223. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Андрей (??), 19-Фев-17, 15:48 
> Какой аллокатор напишешь

Так можно и язык свой написать. Я говорю о тех, что под капотом в glibc и в stdlibc++. По-умолчанию (начиная с какого-то размера объекта, наверное), он тоже не предсказуем. Да ещё и куча фрагментируется.

Ответить | Правка | Наверх | Cообщить модератору

219. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Аноним (-), 18-Фев-17, 22:04 
Ты ничего не смыслишь в программировании.
Ответить | Правка | К родителю #189 | Наверх | Cообщить модератору

104. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 17:19 
>> Никогда не понимал, зачем нужен сборщик мусора? В С++ его нет, и
>> никаких проблем это не создаёт.
> CVE-2016-7117 - критическая дыра в ядре Linux Рейтинг опасности 10/10

Абы ляпнуть чтоль?

Ядро Linux написано НЕ на С++. Ваш Кэп.

Ответить | Правка | К родителю #65 | Наверх | Cообщить модератору

110. "Релиз языка программирования Go 1.8"  +2 +/
Сообщение от Василий Теркин (?), 17-Фев-17, 17:37 
>>> Никогда не понимал, зачем нужен сборщик мусора? В С++ его нет, и
>>> никаких проблем это не создаёт.
>> CVE-2016-7117 - критическая дыра в ядре Linux Рейтинг опасности 10/10
> Абы ляпнуть чтоль?
> Ядро Linux написано НЕ на С++. Ваш Кэп.

Писали бы на С++ вообще бы Линукса до сих пор не было.

Ответить | Правка | Наверх | Cообщить модератору

113. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 17:42 
Что за перевод темы такой? Пассаж про CVE-2016-7117 не в тему к С++ был, так или нет?
Ответить | Правка | Наверх | Cообщить модератору

145. "Релиз языка программирования Go 1.8"  +/
Сообщение от Василий Теркин (?), 17-Фев-17, 18:19 
> Что за перевод темы такой? Пассаж про CVE-2016-7117 не в тему к
> С++ был, так или нет?

Все в тему. С и ассемблер тоже без мусорки. Но и без ООП со всякими с++ плюшками. Поэтому разрабы до сих пор не рискуют переводит код ядра на с++. Слишком большой код и слишком малдо времени, чтобы его отладить.

Ответить | Правка | Наверх | Cообщить модератору

174. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 17-Фев-17, 21:17 
> Ядро Linux написано НЕ на С++. Ваш Кэп.

На Go что ли? Если серьезно, причем здесь ядро вообще?

Ответить | Правка | К родителю #104 | Наверх | Cообщить модератору

183. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 17-Фев-17, 23:23 
> > Никогда не понимал, зачем нужен сборщик мусора? В С++ его нет, и
> > никаких проблем это не создаёт.
> Примерчик с пылу с жару:
> CVE-2016-7117 - критическая дыра в ядре Linux Рейтинг опасности 10/10

Ядро Linux это примерчик того, что в C++ нужен сборщик мусора?
Ну вот как, как к таким умозаключениям приходят?

P.S.
Эта критическая дыра не зависит от сборщика мусора в C++,
так как ядро Linux не на C++ написано.

Ответить | Правка | К родителю #65 | Наверх | Cообщить модератору

93. "Релиз языка программирования Go 1.8"  +4 +/
Сообщение от Аноним (-), 17-Фев-17, 16:26 
Да-да, С++ нахваливают, что память нужно вручную освобождать и юзают при этом умные указатели
Ответить | Правка | К родителю #55 | Наверх | Cообщить модератору

109. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 17-Фев-17, 17:37 
Взаимоисключающие утверждения?
Ответить | Правка | Наверх | Cообщить модератору

134. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 17-Фев-17, 18:03 
Как раз вручную память освобождать не следует. И язык позволяет обходится без этого непотребства и сборщика мусора одновременно.
Ответить | Правка | К родителю #93 | Наверх | Cообщить модератору

96. "Релиз языка программирования Go 1.8"  +/
Сообщение от Толл (?), 17-Фев-17, 16:35 
>>Никогда не понимал, зачем нужен сборщик мусора? В С++ его нет, и никаких проблем это не создаёт.

Сильное утверждение. Проверять я его, конечно же, не буду. (с)

Ответить | Правка | К родителю #55 | Наверх | Cообщить модератору

135. "Релиз языка программирования Go 1.8"  –4 +/
Сообщение от Аноним (-), 17-Фев-17, 18:05 
Вот и создатели Go не стали. И получилось что имеем - большой костылище для решение проблемы, решаемой простой структурой - умным указателем.
Ответить | Правка | Наверх | Cообщить модератору

154. "Релиз языка программирования Go 1.8"  +2 +/
Сообщение от Mike Lee (?), 17-Фев-17, 18:45 
Точно. Засунем все в смартпоинтеры, потрахаемся с копированием, удалим auto_ptr потому что не работает, добавим мув семантики, но будем понтоваться, что сборщик мусора не нужен.
Ответить | Правка | Наверх | Cообщить модератору

201. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Аноним (-), 18-Фев-17, 17:56 
Смарт поинтеры нужны в единичных случаях, т.к. обычно достаточно контейнеров. В мув семантике ничего сложного нет, rvalue ссылки + конструктор перемещения, осваивается минут за 10. Смарт поинтера по сути 2 - unique_ptr для единоличного владения и shared_ptr для множественного. Проблемы по сути нет, а уж воротить для её решения GC - верх иди
Ответить | Правка | Наверх | Cообщить модератору

98. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Василий Теркин (?), 17-Фев-17, 17:05 
> Никогда не понимал, зачем нужен сборщик мусора? В С++ его нет, и
> никаких проблем это не создаёт.

Прогони в С++
class Node {
public:
        Node* next;
};
for (int i = 0; i < 10000000; i++) {
        Node* v = new Node();
}

А потом в С#
class Node
{
    public Node next;
}
for (int l = 0; l < 10000000; l++)
{
    var v = new Node();
}

Если в сях еще прикрутить delete, то ты поймешь преимущество GC сишарпа по рантайму. Да, конечно, примерчик так себе, но показателен. Аллокаторы тоже жрут ресурсы, представь себе!

Ответить | Правка | К родителю #55 | Наверх | Cообщить модератору

101. "Релиз языка программирования Go 1.8"  +/
Сообщение от Василий Теркин (?), 17-Фев-17, 17:14 
> Прогони в С++

Стырено в https://habrahabr.ru/post/148657/
Но смысл понятен. Сборщик мусора, оптимизированный под эффективную работу с кучей для приложения, будет предпочтительней "ручного управления". Разработчику не придется придумывать свой "велосипед" и тратить лишнее время на оптимизацию кода, добиваясь приемлимого рантайма. Время - деньги. Да, конечно, в особо экзотических случаях ручное управление дает большее пространство для маневра в плане производительности. Но в крупных проектах это так же приводит к неприемлимым срокам сдачи. Одно дело написать драйвер устройства, и совсем другое - распределенную систему управления банковскими транзакциями. Накладные расходы, связанные с наличием сборщика мусора решаются другими способами, на уровне реализации системы в целом, а не на уровне кода приложения.

Ответить | Правка | Наверх | Cообщить модератору

139. "Релиз языка программирования Go 1.8"  –2 +/
Сообщение от Аноним (-), 17-Фев-17, 18:11 
> Да, конечно, примерчик так себе, но показателен

Не показателен. Так никто не пишет. Для С# это вполне нормальный код, т.к. разработчик не должен знать как всё устроено внутри и язык не должен выполнять код буквально. C++ же дает гарантии, что код будет выполнен точно так, как напишет программист. Поэтому программист должен понимать как и что работает, и писать правильно.

Ответить | Правка | К родителю #98 | Наверх | Cообщить модератору

143. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Аноним (-), 17-Фев-17, 18:17 
> Поэтому программист должен понимать как и что работает, и писать правильно.

Только вот считающих, что уж они понимают, как что-то работает, во все времена было больше
действительно понимающих. Особенно, если важна не только принципильная схема, но и нюансы.

Ответить | Правка | Наверх | Cообщить модератору

151. "Релиз языка программирования Go 1.8"  +1 +/
Сообщение от Василий Теркин (?), 17-Фев-17, 18:31 
>> Да, конечно, примерчик так себе, но показателен
> Не показателен. Так никто не пишет. Для С# это вполне нормальный код,
> т.к. разработчик не должен знать как всё устроено внутри и язык
> не должен выполнять код буквально. C++ же дает гарантии, что код
> будет выполнен точно так, как напишет программист. Поэтому программист должен понимать
> как и что работает, и писать правильно.

Ну тогда напиши код для cpp "правильно", сделав тоже самое, но за меньшее время чем это делается сишарпе. Задачка-то простая.

Ответить | Правка | К родителю #139 | Наверх | Cообщить модератору

166. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 19:37 
Да запросто:

{
}

(компилятор соптимизировал всё в ноль)

Ответить | Правка | Наверх | Cообщить модератору

202. "Релиз языка программирования Go 1.8"  +/
Сообщение от Аноним (-), 18-Фев-17, 17:59 
Решение предельно простое, не выделять память 10000000 раз, как ииот.
Ответить | Правка | К родителю #151 | Наверх | Cообщить модератору

150. "Релиз языка программирования Go 1.8"  +3 +/
Сообщение от Ivan (??), 17-Фев-17, 18:30 
Не хочется кормить тролля, но один раз отвечу.

Данный пример ничего полезного не делает и clang 3.9.1 компилирует его в функцию из одной инструкции ret: https://godbolt.org/g/aKZsWT Я думаю можно с уверенностью сказать, что нет ничего быстрее, чем пустая функция.

Но это всё благодаря оптимизации, когда мы видим, что память выделилась и тут же освободилась мы можем заменить аллокацию в хипе на аллокацию в стеке. GCC такую оптимизацию не делает. Я не знаю, про какую реализацию .NET ты говоришь, но приведенный код тоже может быть соптимизирован в ничто.

Хочу обратить внимание, что данный код на C++ пессимизирован и правильнее было бы создавать объект в стеке, просто: Node v; Тогда оба компилятора и clang и GCC компилируют код в пусто.

С бенчмарками есть одна проблема. Существует множество различных программ, в бенчмарке автор выбирает одну из них и сравнивает на ней. Вопрос, почему мы считаем этот один пример вообще репрезентативным?

Я хочу обратить внимание вот на какой факт. Все современные аллокаторы памяти работают для маленьких объектов (до ~1kb, а это 99.9% всех объектов) за O(1). Все современные GC так или иначе обходят весь хип, это может по разному называется, но это происходит. Они стараются делать это как можно реже (применяют гипотезу поколений, используют счетчики ссылок, чтобы не обходить, когда не возникают циклы -- разные делают разному), но это всё равно проиходит. То есть мы сравниваем O(1) и O(размера хипа).

Есть ещё один момент компирующие сборщики мусора копируют объекты. Как правило увеличение размера объектов приводит к тому, что GC случаются чаще и копировать памяти нужно больше. Т.е. GC чувствителен к размеру наших объектов. Обычные аллокаторы памяти на 64-битных системах к этому не чувствительны.

Таким образом по мере роста размера хипа и увеличения размера объектов GC будет работать всё хуже и хуже по сравнению с обычным аллокатором памяти. Конечно обычные бенчмарки обычно проводятся в условиях почти идеальных для GC (маленькие объекты, маленький хип).

Ещё один способ наврать в бенчмарках это заточиться на гипотезу поколений и сделать так, чтобы все объекты умирали не выходя из Gen0, собственно, что ты сделал в своем примере. Но ответ на это очень простой -- если объект коротко живущий его надо создавать в стеке. И если мы для коротко живущих объектов будем использовать стек, то на долго живщих обычный аллокатор, скажем jemalloc или tcmalloc, порвет на тряпки дотнетовский Gen2 GC.

Ответить | Правка | К родителю #98 | Наверх | Cообщить модератору

161. "Релиз языка программирования Go 1.8"  +2 +/
Сообщение от Василий Теркин (?), 17-Фев-17, 18:55 
> Не хочется кормить тролля, но один раз отвечу.

Спасибо за развернутый ответ. Но я НИКОГДА и не спорил, что в С++ с его гибкостью нельзя решить задачку идеально, по сравнению с другими ЯП. Но, за это придется заплатить. 1. Время разработки/отладки 2. Квалификация программиста. И 90% программистов будут писать код "что вижу то и пишу", и без дополнительных механизмов повышения качества конечного продукта, увы, не обойтись. Поэтому Java в свое время оккупировала рынок энтерпрайз систем, вытеснив с этой ниши С и С++. Как я уже говорил, в некоторых случаях скорость разработки РАБОТОСПОСОБНОГО решения превалирует над макисмальной возможной скоростью его быстродействия. А требования к надежности и предсказуемости работы кода еще более сужают нишу применения с++. Высококлассных программистов в наше время не так уж и много, чтобы решать весь спектр существующих задач. ЯП - всего лишь инструмент. И если этот инструмент решает поставленные задачи - это хороший инструмент. А беседы об идеальных инструментах на все случаи жизни - это уже из разряда религий и верований.

Ответить | Правка | Наверх | Cообщить модератору

167. "Релиз языка программирования Go 1.8"  –1 +/
Сообщение от Аноним (-), 17-Фев-17, 19:45 
А что про Python и Ruby скажете? Скорость разработки на них выше, чем на Java. И, подозреваю, выше, чем на Go. Считаете, что дольше надо будет добиваться РАБОТОСПОСОБНОГО решения?
Ответить | Правка | Наверх | Cообщить модератору

228. "Релиз языка программирования Go 1.8"  +/
Сообщение от Василий Теркин (?), 20-Фев-17, 14:56 
Ну вроде оба этих языка относятся к интерпретируемым(за исключением отдельно привязываемых костылей). И у обоих есть сборщики мусора. И если решение на этих языках конкретных задач более эффективно, чем на GO или С++, то я отношусь к этим языкам весьма положительно. И буду дальше добиваться РАБОТОСПОСОБНОГО приложения, по причине того, что НЕРАБОТОСПОСОБНЫЕ никому не нужны, кроме их авторов.
Ответить | Правка | Наверх | Cообщить модератору

Архив | Удалить

Рекомендовать для помещения в FAQ | Индекс форумов | Темы | Пред. тема | След. тема




Партнёры:
PostgresPro
Inferno Solutions
Hosting by Hoster.ru
Хостинг:

Закладки на сайте
Проследить за страницей
Created 1996-2024 by Maxim Chirkov
Добавить, Поддержать, Вебмастеру