Создать подпрограмму go просто, так как процедура go легковесна, мы можем создать тысячи подпрограмм go для выполнения задач. Но каждая процедура имеет свою стоимость - затраты на потребление ресурсов, таких как использование памяти или ЦП.

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

Проблема потребления ресурсов и невыполнения их после завершения приведет к уменьшению количества доступных ресурсов для запуска других процессов. Это приведет к постоянному зависанию системы и резкой загрузке процессора. Код, который выполнялся в 10 раз быстрее после использования подпрограмм go, начнет работать так же медленно, как в 100 раз по сравнению с предыдущим кодом. Иногда единственный способ решить эту проблему - выключить компьютер.

Один из способов - назначить ограниченный ЦП нашему коду golang с помощью пакета времени выполнения и выделить ограниченные ресурсы, но это не решит проблему. Мы должны внедрить постоянное решение этой проблемы. Назначение подпрограммам объема работы и их закрытие после завершения назначенной задачи - лучший способ справиться с ней.

Давайте рассмотрим несколько примеров рутинной утечки информации.

Вышеупомянутый код будет работать, как ожидалось, без ошибок, но процедура go будет продолжать работать из-за того, что цикл for никогда не заканчивается, что вызывает утечку, поскольку нет сигнала или способа остановить его в случае ошибки.

Давайте посмотрим на другой пример утечки подпрограмм go при запуске нескольких подпрограмм go, которые вместе пишут в один и тот же канал.

Поскольку мы используем для выбора вариант по умолчанию, тупиковая ситуация в рутине не возникает. Несмотря на то, что программа запускается несколько раз, есть вероятность, что значения, переданные в канал, никогда не будут получены, например, в случае запросов REST api.

Существует сторонний пакет, созданный, чтобы выяснить, есть ли утечка внутри программы, запустив тесты. Пакет с открытым исходным кодом используется в качестве стандартного течеискателя https://github.com/uber-go/goleak. Я использовал тот же пакет, чтобы узнать, есть ли утечки в запущенных в программе процедурах go.

После создания тестового файла для программы, упомянутой во втором примере. Мы можем запустить тестовый файл, используя go test. Он вернет номер процедуры go, выполнение которой не удастся. Затем нам нужно проверить место возникновения обычной утечки и устранить ее.

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

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

Вывод: - Использовать подпрограммы go несложно, но управлять ими важно, чтобы убедиться, что наше программное обеспечение будет работать эффективно в долгосрочной перспективе. Если не обработать должным образом, это приведет к блокировке процесса и потреблению больших ресурсов процессора и памяти для выполнения небольшого фрагмента кода. Следите за обновлениями….