Интерфейсы в Go

В этом посте речь пойдет об интерфейсах — очень важной и интересной фиче языка Go. Абстрактные типы данных Для того чтобы лучше понять интерфейсы, полезно разобраться с понятием абстрактных типов данных. Упрощённо абстрактные типы данных можно определить как типы, у которых не может существовать собственных значений. Справедливый вопрос: а зачем такие типы тогда нужны? АТД в первую очередь определяет требования к «обычному» типу данных. Если тип соответствует требованиям, то говорят, что он является реализацией для АТД, а значит, может быть использован в переменных, полях и сигнатурах, где в качестве типа был указан реализуемый АТД. Например, над любыми числами можно совершать любые, за некоторыми исключениями, арифметические операции. Следовательно, можно объявить абстрактный тип Число, разными реализациями которого будут натуральные, целые, рациональные, вещественные и комплексные числа. Если не важны специфические свойства какого-либо множества чисел, то гораздо удобнее оперировать более абстрактным понятием числа. Интерфейсы Интерфейс является частным случаем, а в языке Go — по сути единственным представителем семейства АТД. Интерфейсы используются, чтобы описать, каким набором методов должна обладать его реализация. Это полезно, когда нас интересует только поведение некоторой сущности, но совсем не интересуют детали реализации. Это в свою очередь помогает снизить связность компонентов приложения и упрощает сопровождение кода. Давайте взглянем на стандартную библиотеку языка. Она содержит много интерфейсов, которые похожи на то, что авторы языка называют хорошим и идиоматичным интерфейсом. Одни из самых используемых — знаменитая тройка Writer, Reader, Closer, интерфейсы из пакета io: 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 type Writer interface { Write(p []byte) (n int, err error) } // ... type Reader interface { Read(p []byte) (n int, err error) } // ... type Closer interface { Close() error } В данных трёх типах можно увидеть идиоматику интерфейсов в Go:...

January 15, 2022  7 min

Завершаем правильно программы на Go

Если завершение вашей программы или, если хотите, сервиса вы отдаёте полностью на откуп операционной системе, скорее всего это не самый верный путь. И в этом материале мы разберёмся, почему. Для чего нужен Graceful Shutdown Вы наверняка слышали такое словосочетание как stateless service. Это сервис, который не хранит никакого состояния внутри себя, а делегирует эту задачу внешнему хранилищу. Под состоянием чаще всего имеют ввиду данные. Стремление к тому, чтобы сервис был “stateless”, т.е. свободным от состояния, является хорошей архитектурной практикой, поскольку облегчает жизнь, когда дело доходит до масштабирования. Иногда это «правило» игнорируется для повышения производительности. Например, большинство современных СУБД хранит часть актуальных данных не на диске, а прямо в памяти процесса. Периодически и, самое главное, перед завершением процесса СУБД актуализирует эти данные на диске. Если всё, что делает сервис это принимает a и b, и возвращает a+b, то никаких проблем нет, поскольку у сервиса в данном случае нет состояния. Скорее всего большая часть сервисов, которые вы разрабатываете или будете разрабатывать устроены несколько сложнее. Даже если они свободны от состояния в классическом понимании, но обращаются к СУБД, диску или другим сервисам, они всё ещё обладают состоянием, просто оно выражено не данными, а ресурсами. Почему ресурсы, которые мы запрашиваем у операционной системы необходимо освобождать — тема отдельного разговора. Сейчас давайте примем как аксиому, что за очисткой ресурсов важно следить. Системные ресурсы можно разделить на два вида: С коротким жизненным циклом — например, чтение конфигурационного файла или соединение для REST-запроса. Обычно освобождаются сразу после использования. С неопределённым жизненным циклом — вебсокеты, стриминг, консьюминг из очереди, кэш на диске и т.д. Информация, которую они предоставляют, требуют быстрого доступа, поэтому такие ресурсы занимаются редко, но надолго. Второй тип ресурсов я назвал так именно потому, что скорее всего мы не знаем, когда нам придётся их очистить....

December 31, 2021  8 min

Разбираемся с контекстами в Go

Этот пост является конспектом моего видео про контексты: Я заметил, что тема контекстов в языке Go у многих почему-то вызывает сложности с пониманием. Возможно, это связано с тем, что контекст — это очень абстрактная сущность и не встречается в других языках программирования в таком виде, по крайней мере в тех языках, что довелось использовать мне. В общем, я решил написать материал по данной теме с примерами и лучшими практиками. Вам будет легче понять то, о чем я буду рассказывать, если вы уже знакомы с основами языка Go, в частности знаете, что такое горутины и каналы. Что такое контекст? Если мы взглянем на документацию к пакету context, то первый абзац будет таким: Package context defines the Context type, which carries deadlines, cancellation signals, and other request-scoped values across API boundaries and between processes. Пакет context определяет тип Context, который позволяет управлять дедлайнами, сигналами отмены и другими значениями области действия запросов между границами API и процессами. Что это, чёрт побери, значит? А значит это примерно следующее: Контекст — это объект, который предназначен в первую очередь для того, чтобы иметь возможность отменить извне выполнение потенциально долгой операции. Кроме того, с помощью контекста можно хранить и передавать информацию между функциями и методами внутри вашей программы. Отменять долгие операции с помощью контекста можно несколькими способами: По явному сигналу отмены (context.WithCancel) По истечению промежутка времени (context.WithTimeout) По наступлению временной отметки или дедлайна (context.WithDeadline) Пример. Столик в ресторане Вы хотите забронировать столик в ресторане. Для этого вы набираете ресторан, и ждете, пока на той стороне возьмут трубку. Далее происходит одно из двух: Сотрудник ресторана берёт трубку. В таком случае вы начинаете диалог — всё хорошо; На той стороне никто не берёт трубку в течение минуты, двух, трёх…...

December 5, 2021  9 min

Как начать печатать быстро

Не так давно я задумался о том, что было бы неплохо поднять скорость набора текста. Это не является для меня чем-то необходимым, поскольку IDE придёт на помощь, но меня страшно бесит, что я делаю много опечаток, и длинные сообщения в мессенджерах или по почте приходится набирать неприлично долго. Голосовой ввод в таком случае тоже не спасает — всё-таки его результат требует коррекций. Поэтому летом 2020 года я начал погружаться в тему скоропечатания, и данный пост — концентрация опыта и знаний, которые у меня накопились к моменту написания. 10-пальцевый набор вслепую Главный принцип и идея скоропечатания — в использовании десяти (или меньше, если пальцев меньше) пальцев руки при наборе текста. При этом вы не смотрите на клавиатуру в поисках нужной клавиши — взгляд направлен на экран. Можно игнорировать данный метод, объясняя это тем, что, мол, «я и используя 7 пальцев быстро печатаю». Я именно так и считал, и первое время использование всех пальцев даже снизило мою среднюю скорость. Однако на длинной дистанции это даёт заметный профит, в чём я убедился лично. Основные две метрики, использумые при оценке: Words Per Minute — количество слов в минуту; Точность — доля символов, напечатанных правильно с первого раза. Это очевидно, и наверняка вы уже об этом слышали. Пусть это будет для затравки. Как тренироваться Далее перечислены правила, которые я соблюдаю сам, потому что для меня они работают. Часть из них я вывел сам, другую часть прочитал или увидел в других источниках. Фокусируйтесь на точности, а не на скорости Это звучит контринтуитивно, но в первую очередь эффективнее тренировать точность вместо скорости. Если разобраться, то на деле всё просто. Когда вы делаете опечатку, время уходит не только на исправление ошибки, но и на то, чтобы заметить опечатку. Представим, что вы нажимаете 5 клавиш в секунду, но делаете одну ошибку....

December 21, 2020  13 min

Кумиров больше не будет

Можно легко назвать почти всех великих композиторов последних нескольких веков. У каждого десятилетия прошлого века были свои кумиры. И мне кажется, кумиры в привычном смысле всё. Вряд ли с каждым поколением, живущем в наш век, будут прочно ассоциироваться какие-то определенные музыканты. Дело в том, что производство музыки стало настолько доступным во всех смыслах этого слова, что хороших композиторов, саунд-продюсеров, битмейкеров и музыкантов стало слишком много. Да и сама музыка сейчас куда доступнее, а точнее практически бесплатна. Серьёзно, я каждый день обнаруживаю в Спотифае очень талантливых чуваков, и я не могу сказать, что кто-то лучше, а кто-то хуже — они все одинаково круты. Безусловно, у меня всё ещё есть список моих самых любимых авторов и песен, но и он, оказывается, резиновый. На самом деле эта тенденция наблюдается не только в музыке — кроме средств звукоизвлечения доступнее становятся кино, разработка игр, актёрское мастерство, фотография, изобразительное искусство, образование, знания, компьютеры, ремонт, вождение, …, ну вы поняли. Что с этим делать? А вообще, проблема ли это? Чёрт его знает. Лично я просто наслаждаюсь изобилием.

October 30, 2020  1 min

Плёночный Петербург (и немного Выборг)

October 29, 2020  0 min

Получение опыта из других областей

Я очень долго не мог поладить с Unity. В основном мои проблемы сводились к тому, что связность компонентов любой игры, которую я создавал с использованием этого движка, очень быстро росла. Я знал об этом, но не знал, что с этим делать. В итоге каждое новое изменение в коде игры давалось всё сложнее. Рост сложности кодовой базы выглядел примерно так. На самом деле всё не так плохо, но суть, я надеюсь, ясна. Что интересно, ни с каким из движков, с которыми я работал до этого, таких проблем не возникало. Поэтому я начал полагать, что это с Unity что-то не так, и мне просто нужно сменить движок. Unreal Engine я отмёл сразу, т.к. вся его мощь была для меня избыточной. Я посмотрел в сторону Godot Engine. Где-то на пятом часу его изучения познакомился с местной концепцией сигналов. Немного порефлексировав после, я понял, что это очень похоже на то, что я встречал в других движках и фреймворках и именно то, чего мне не хватало в Unity. После того как я стал использовать паттерны и концепции реактивного программирования в Unity, разработка игр стала идти как никогда плавно и без лишней нервотрёпки. К чему я это всё рассказываю? Даже если вы считаете себя специалистом очень узкого профиля, но планируете повышать свою экспертизу и свои навыки, важно подглядывать в смежные технологии и области и знакомиться с идеями оттуда. Это позволит смотреть по-другому на привычные вещи. Конечно, это не значит, что нужно быть абсолютным фуллстэком (читай мастером на все руки, но руки из одного места). Всё должно быть в меру, и лучше, если приобретаемые навыки положительно влияют на основные компетенции.

October 28, 2020  2 min

О пресетах

Очень долгое время мне казалось, что использовать пресеты (ранее предустановленные параметры) синтезаторов или семплы — это халтура. Всегда думал, что настоящие профессионалы настраивают синтезаторы на желаемое звучание с исходных настроек. Мне не было достаточно многочисленных лекций о том, что все используют семплы, и что это нормально. Мнение поменялось, когда я наткнулся на две любопытные ситуации, связанные с виртуальным синтезатором Sylenth1. Hotline Miami По моему мнению, Hotline Miami — настоящее произведение искусства. В игре, сделанной на конструкторе, прекрасно всё: визуальный стиль, сеттинг, сюжет, геймплей и музыка. Особенно музыка. Во многом благодаря превосходному саундтреку, которым можно наслаждаться вне контекста игры, а значит, делиться с друзьями, игра обрела популярность и коммерческий успех. Но есть одно но: трек M.O.O.N. — Dust, являющийся главной темой игры, использует в качестве главной мелодии пресет Sylenth1. Что интересно, пресет даже никак не перенастроен, т. е. в секвенсоре не была изменена хотя бы одна нота. Стало ли это скандалом? Конечно, нет. Трек определенно хорош, хоть и не заседал бы так в голове, не будь в его основе той самой мелодии из пресета. А если никто от этого не пострадал, то ничего плохого в этом и нет. Фильм “Ex Machina” и The Prodigy При прослушивании трека «Wild Frontier» с последнего альбома группы моего детства, The Prodigy, меня не покидало странное ощущение. Первые несколько секунд казались до боли знакомыми, а в голове в это время неизбежно появлялся образ Донала Глисона. Так продолжалось несколько месяцев, и связь между рыжим ирландским актёром и вступлением песни не хотела проявляться. Был как-то день, когда мне захотелось переслушать саундтрек к научно-фантастическому фильму «Ex Machina». На одной из композиций меня стало беспокоить в точности то же чувство. Ben Sailsburry & Geoff Barrow — Bunsen Burner Донал Глисон исполнил в фильме главную роль....

October 25, 2020  3 min

Парадокс глобальных стандартов

Как-то раз я забыл зарядник для телефона у друзей, но понял это уже вечером, когда телефон полностью разрядился. Я бы мог взять и подключить к телефону любой зарядник: от бритвы, от ноутбука, от чего угодно. Но они не подходят к разьёму micro USB. Это заставило меня задуматься вот о чём: почему производители электроники не делают разъёмы в своих устройствах такими, что к ним будут подходит любые или почти любые зарядники? Конечно, иногда это имеет вполне рациональные корни: например, к телефону бренда N подходит зарядник только бренда N. Тогда N может заработать больше денег. Но так не всегда. Очень редко бывает так, что друг, находясь у вас в гостях, просит зарядник от вашей электробритвы, чтобы зарядить свою. Я не сильно разбираюсь в электронике на низком уровне, поэтому, если что, поправьте меня. Но разве есть какие-то проблемы с тем, чтобы все мелкие и средние электронные устройства использовали один разъём, но с разной пропускной способностью? Хотя какие-то уверенные шаги в этом направлении всё-таки делаются: например, Apple переходит на использование только лишь USB Type-C для любых подключаемых устройств. Я полностью поддерживаю данную инициативу, хотя с любым таким радикальным шагом можно связать один интересный момент — стадию глобального перехода на новый стандарт. Данный феномен связан не только с этими чёртовыми разьёмами, а в целом с моментами, когда повсеместно используемый технологический стандарт получает обновление. Естественно, новую версию не сразу поддерживают все объекты, которые его используют. В случае с ПО и интернетом, при условии грамотной разработки стандарта, это не так критично из-за обратной совместимости: всё больше веб-сервисов переходит на HTTPS, но при этом HTTP работает так же хорошо, как и раньше, и вообще с ним никаких проблем в работе (не считая безопасности, которая и стала причиной перехода на HTTPS) с точки зрения и пользователя, и разработчика нет....

October 25, 2020  2 min