1.82K subscribers
3.08K photos
121 videos
15 files
3.42K links
Блог со звёздочкой.

Много репостов, немножко программирования.

Небольшое прикольное комьюнити: @decltype_chat_ptr_t
Автор: @insert_reference_here
Download Telegram
#go #quotes

(опубликовано с разрешения автора)
#prog #go

Вышла версия Go 1.21.

В число невероятных изменений входят:

* новые встроенные функции min и max
* новая встроенная функция clear для удаления всех элементов из мапы и зануления элементов слайса (???)
* File.Chdir теперь действительно меняет текущую рабочую директорию на Windows вместо того, чтобы всегда возвращать ошибку

А ещё добавили — экспериментально! — способ сделать поведение переменных цикла более вменяемым: каждая итерация цикла создаёт новую переменную вместо переиспользования одной и той же.
#go

(thanks @repushko)
#prog #go #article

What’s New in Go 1.22: slices.Concat

<...>

Early versions of the Concat proposal included a destination slice argument, like append. (Concat(dest []T, ss ...[]T) []T.) Why doesn’t the final version of slices.Concat have a destination argument to allow users to reuse an existing slice as backing?

The issue
goes back to what is called the problem of aliasing. <...> But what if you are concatenating the parts of a slice onto itself? Take this example:

s := []int{1, 2, 3, 4}
_ = slices.ConcatWithDestination(s[:0], s[3:4], s[2:3], s[1:2], s[0:1])
// What is s now?


A naïve implementation of slices.ConcatWithDestination would clobber the 1 at the start of the slice with 4 before copying it onto the end of the slice, so that you end up with 4, 3, 3, 4 instead of 4, 3, 2, 1 as intended.

<...>

In the end, it was decided that just always returning a new slice would keep the implementation of slices.Concat simpler and help prevent any issues with accidentally aliasing a slice and getting unexpected results, so the destination slice argument was dropped.

(thanks @golang_for_two)
#prog #go

6 февраля вышла версия Go 1.22.

Среди прочего в стандартную библиотеку добавлен пакет math/rand/v2. Примечательно это по двум причинам.

Первая: это первый случай, когда в стандартную библиотеку Go добавляют вторую версию пакета. На мой взгляд, это вполне себе довод в пользу того, чтобы не делать std слишком богатой. (Конечно, тут ещё далеко до безобразия Python с urllib3, но кто знает, может, и до этого дойдёт).

Вторая: в proposal на этот пакет упомянуто следующее:

2. Remove Source.Seed, Rand.Seed, and top-level Seed. Top-level Seed is deprecated as of Go 1.20. Source.Seed and Rand.Seed assume that the underlying source can be seeded by a single int64, which is only true of a limited number of sources. Specific source implementations can provide Seed methods with appropriate signatures, or none at all for generators that cannot be reseeded; the details of seeding do not belong in the general interface. [выделение моё]

В оригинальном дизайне rand получение случайных значений действовало через тип Rand, который оборачивал значение, реализующее интерфейс Source:

type Source interface {
Int63() int64
Seed(seed int64)
}

В v2 метод Seed убрали, а метод Int63 поменяли на Int64 — и совершенно верно, ибо в этом интерфейсе торчали уши конкретной дефолтной реализации Source. Однако заявление "the details of seeding do not belong in the general interface", как мне кажется, вызвано не общими соображениями, а ограничениями Go. Именно, в идеале у каждого источника случайности должен быть свой тип для сида — но в Go нельзя сделать тип, который является частью интерфейса и который может быть определён реализацией.

Для сравнения, в растовом rand инициализация из начального значения вынесена в отдельный трейт SeedableRng, где сид определяется через ассоциированный тип.

===========

Другая вещь, которая куда как более стрёмная — это тот факт, что тип Rand может запрашивать данные из Source только через метод Int64, а потому остальные методы не могут эксплуатировать тот факт, что они работают с конкретным типом источника случайности, и потому не могут использовать специфичные для этих типов оптимизации. В частности, реализация Rand.Int32 попросту зовёт Int64 на внутреннем Source и делает битовый сдвиг, отбрасывая младшие 33 бита. Если Rand.Int32 вызывается в цикле, то выходит, что где-то половина работы источника случайности уходит в никуда.
#prog #go #article

Hiring Challenge: Smallest Golang Websocket Client

TL;DR: если опуститься до голых сисколов, выкинуть GC, пошаманить с линкером для выкидывания лишних секций и компилировать под 32 бита, то можно уменьшить размер на четыре порядка по сравнению с бейзлайном.

Занятно, что избавление от std уменьшает размер вдвое по сравнению с предыдущим шагом. gc слаб в LTO?

(thanks @go_perf)
#prog #go #article

Go channels are bad and you should feel bad

Статья из 2016 года, поэтому претензии касательно отсутствия дженериков не применимы, а некоторые утверждения касательно устройства стандартной библиотеки могли устареть.

In all of my Go code I work with, I can count on one hand the number of times channels were really the best choice. Sometimes they are. That’s great! Use them then. But otherwise just stop.