В операторе when — будь он внутри «родного» блока given или внутри цикла for — обычно происходит смартматчинг переменной $_ с указанным выражением. В документации perlsyn перечислены искючения, однако есть и не слишком очевидное поведение, о котором нужно знать.
Вначале о том, что явно указано как исключения. Блок when(EXPR) не выполняет смартматчинг $_ ~~ EXPR, а является просто булевым выражением, если EXPR — одно из следущего:
- Вызов функции или метода.
- Регулярное выражение (тут надо помнить, что операторы =~ и ~~ ведут себя по-разному).
- Сравнение (как с переменной по умолчанию, так и с любой друой) или явный смартматчинг.
- Отрицание (!, not или xor).
- Файловый тест.
- Операторы .. и ....
А теперь о том, где можно наступить на грабли. В предыдущей заметке встречались выражения типа
when(0b1110_0000 == ($_ & 0b1111_0000))
Дополнительная проверка на равенство здесь необходима (даже если проигнорировать младшие биты). Прямолинейная битовая операция
when($_ & 0b1111_0000)
сравнивает переменную $_ со значением, полученным после битовой операции $_ & 0b1111_0000, и для проверки установленных битов нужно выполнять явное сравнение, которое входит в один из пунктов перечисленных выше исключений.
Комментировать