#go #goroutine
#Вперед #goroutine
Вопрос:
Есть ли способ заставить программу запускать X раз в секунду, независимо от того, есть ли другие программы, которые могут выполнять интенсивную работу с процессором?
Небольшая справка о том, почему, я работаю на игровом сервере, написанном на go, у меня есть подпрограмма, которая обрабатывает игровой цикл, игра обновляется со скоростью X тактов в секунду, конечно, некоторые операции, выполняемые сервером, являются дорогостоящими (например, генерация местности), в настоящее время я просто появляюсьпрограмма goroutine и позволяет ей обрабатывать генерацию таким образом, чтобы не блокировать подпрограмму gameloop, но после тестирования на сервере с одним vcore я увидел, что она по-прежнему блокирует gameloop при выполнении операций с интенсивным использованием процессора.
После поиска в Интернете я обнаружил, что go не будет перепланировать подпрограмму, пока она не находится в блокирующем системном вызове, теперь я мог бы поступить так, как было предложено, то есть просто вручную вызвать reschedule для подпрограммы, но у этого есть две проблемы: это сделает код с интенсивным использованием процессора более запутанным, с необходимостью обработки тайм-аутовв определенные моменты и даже после ручного перепланирования он может просто перепланировать другую программу с интенсивным использованием процессора вместо игрового цикла…
Комментарии:
1. Это больше не соответствует действительности: «… go не будет перепланировать подпрограмму, пока она не находится в блокирующем системном вызове». Какую версию go вы используете? Начиная с версии 1.14, подпрограммы могут быть выгружены.
2. Я нахожусь на 1.15.2, возможно ли, что он не выгружается достаточно быстро, чтобы игровой цикл выполнялся со скоростью X тактов в секунду?
3. Если вам нужно запустить программу X раз в секунду, используйте тикер, чтобы получать тик X раз в секунду, измерьте, и если он не может составить расписание, начните искать обходные пути.
4. Да, в настоящее время я использую тикер, я думаю о том, чтобы просто создать выделенный поток для игрового цикла вместо этого … просто надеялся, что есть лучший способ сделать это…
Ответ №1:
Есть ли способ заставить программу запускать X раз в секунду, независимо от того, есть ли другие программы, которые могут выполнять интенсивную работу с процессором?
НЕТ
после тестирования на сервере с одним vcore я увидел, что он по-прежнему блокирует игровой цикл при выполнении операций с интенсивным использованием процессора.
Чего еще вы ожидаете? У вас есть одно ядро и две операции, которые необходимо выполнить.
После поиска в Интернете я обнаружил, что go не будет перепланировать подпрограмму, пока она не находится в блокирующем системном вызове
Неверно.
Из go runtime:
Goroutines are now asynchronously preemptible. As a result, loops without function calls no longer potentially deadlock the scheduler or significantly delay garbage collection. This is supported on all platforms except windows/arm, darwin/arm, js/wasm, and plan9/*.
Комментарии:
1. Мне интересно, есть ли способ заставить другую подпрограмму выгружать, пока должен выполняться игровой цикл. Текущее поведение имеет смысл, оно просто не то, что я хочу… и да, я ошибался в этом переносе, к сожалению, большинство сообщений, которые я видел, датированы парой лет назад…
2. @ItayAlmog То, о чем вы просите, — это установить приоритет для подпрограмм. Эта концепция широко обсуждалась и, к сожалению, для вас, но она отклонена. groups.google.com/g/golang-dev/c/HJcGESXfJfs