Я хотел попробовать тест FizzBuzz (Why can't programmers program) и использовал Go. Это, в основном, цикл от 1 до 100 и печать «Fizz», когда счетчик циклов делится на 3, «Buzz», когда делится на 5, «FizzBuzz», когда они делятся на оба, а просто распечатывают номер.Почему эта функция golang _not_ работает навсегда?
После этого итеративно и рекурсивно, я хотел сделать это одновременно (или используя каналы). Я придумал следующий код, который работал, к моему удивлению:
func fizzbuzzconc() {
// Channels for communication
fizzchan := make(chan int)
buzzchan := make(chan int)
fizzbuzzchan := make(chan int)
nonechan := make(chan int)
// Start go routine to calculate fizzbuzz challenge
go func() {
for i := 1; i <= 100; i++ {
if i % 3 == 0 && i % 5 == 0 {
fizzbuzzchan <- i
} else if i % 3 == 0 {
fizzchan <- i
} else if i % 5 == 0 {
buzzchan <- i
} else {
nonechan <- i
}
}
}()
// When or how does this for loop end?
for {
select {
case i := <-fizzchan:
fmt.Println(i, "Fizz")
case i := <-buzzchan:
fmt.Println(i, "Buzz")
case i := <-fizzbuzzchan:
fmt.Println(i, "FizzBuzz")
case i := <-nonechan:
fmt.Println(i, i)
}
}
}
Я не могу понять, как и почему цикл останавливается. Не существует условия разрыва или оператора возврата. Почему в конечном итоге он заканчивается?
Добавить 'default' на ваш выбор. Любое изменение? – bishop
Когда я добавляю по умолчанию, выполнение выполняется намного медленнее, и оно не выходит. Теперь у меня есть ожидаемое поведение, спасибо. – Kiril
Да. Причина в том, что весь ваш «случай» вводит системный вызов через «Println». Go проверяет состояние канала во время системных вызовов и видит, когда последний из них опустошает все каналы. В этот момент срабатывает детектор тупиковой ситуации и убивает петлю. Когда вы добавляете пустой 'default', есть ветка, которая не проходит через системные вызовы и не проходит через нее. Наименьшее изменение, которое вы можете сделать, чтобы заставить ваш код выйти из строя, заключается в том, чтобы добавить канал группы ожидания в ваш случай по умолчанию, как показано в этом ответе: http://stackoverflow.com/a/21819794/2908724 – bishop