🔴 Сложный · 3 очк. Горутины и конкурентность
При каких операциях горутина может уступить управление планировщику Go?
A Только при явном вызове runtime.Gosched()
B При операциях с каналами, системных вызовах, аллокациях, вызовах функций и с Go 1.14+ - по preemption-сигналу в любой точке
C Только при завершении функции
D Только при блокировке на мьютексе
Объяснение вопроса

Планировщик Go может переключить горутину в следующих точках:

  • Операции с каналами - отправка, получение, select
  • Системные вызовы - файловые, сетевые операции
  • sync-примитивы - Lock, Wait, Cond.Wait
  • Вызовы функций - в прологе функции проверяется необходимость роста стека, это точка preemption
  • runtime.Gosched() - явная уступка
  • Аллокации - вызов GC может приостановить горутины
  • Asynchronous preemption (Go 1.14+) - сигнал SIGURG прерывает горутину в любой точке
// До Go 1.14 этот цикл мог заблокировать поток навсегда:
go func() {
    for { // tight loop без вызовов функций
        i++ // не уступает управление!
    }
}()
// С Go 1.14+ планировщик прервет горутину по сигналу

Asynchronous preemption в Go 1.14 решил проблему "зависших" горутин в tight loops.

🧠Квиз 🏆Лидеры 🎯Собесед. 📖Вопросы 📚База зн.