5.10. Побитовые операции

Арифметические операции на предыдущей странице работают со значениями пикселей – целочисленными яркостями или упакованными цветовыми словами. Побитовые операции работают на один уровень ниже, с отдельными битами внутри этих значений. Для двоичных изображений, где каждый пиксель – это всего лишь один бит, побитовые операции являются естественной арифметикой.

5.10.1. Семейство побитовых операций

Класс Image предоставляет полный набор побитовых операций над двумя входами:

  • b_and() – побитовое И.

  • b_or() – побитовое ИЛИ.

  • b_xor() – побитовое исключающее ИЛИ.

  • b_nand() – НЕ-И.

  • b_nor() – НЕ-ИЛИ.

  • b_xnor() – НЕ-исключающее ИЛИ.

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

Три таблицы истинности для операций И, ИЛИ и исключающего ИЛИ рядом друг с другом. Каждая таблица имеет четыре строки для комбинаций входов 0-0, 0-1, 1-0, 1-1 и столбцы с метками A, B и результат. Под таблицами истинности два небольших двоичных изображения A и B нарисованы в виде сеток черных и белых ячеек, а результат их побитового И показан справа в виде сетки, которая сохраняет только те ячейки, что были белыми в обоих.

Сверху: таблицы истинности И, ИЛИ и исключающего ИЛИ – побитовая семантика каждой операции. Снизу: два двоичных изображения A и B и результат A.b_and(B), где результат сохраняет только те позиции, что были включены в обоих входах.

5.10.2. Объединение масок

Самое распространенное применение этих операций – это объединение масок. Маска – это двоичное изображение, которое сообщает, позиция за позицией, выполнено ли некоторое условие. Две маски, описывающие разные условия, объединяются в одну маску, описывающую составное условие, через одну из побитовых операций:

b_and() создает маску, чьи позиции включены только тогда, когда обе входные маски были включены в этой позиции – естественное «и» двух условий. Объединение маски переднего плана с выводом прохода пороговой обработки через b_and ограничивает совпадения порога передним планом.

b_or() создает маску, чьи позиции включены всякий раз, когда любая входная маска была включена – естественное «или». Применение ИЛИ к двум пороговым выводам создает одну маску, покрывающую все, что совпало с любым из двух цветовых диапазонов.

b_xor() создает маску, чьи позиции включены всякий раз, когда ровно одна входная маска была включена. Полезно для обнаружения позиций, где две маски расходятся – позиций, где пороговый вывод изменился между двумя кадрами, симметрической разницы между двумя эталонными масками и тому подобного.

Отрицающие варианты – b_nand(), b_nor(), b_xnor() – создают дополнение своих неотрицающих аналогов. Они полезны, когда естественный способ описать условие – это «ни одно из этих» или «не оба» – не часто, но стоит знать об их существовании, чтобы отрицание не приходилось составлять, дополняя И отдельным invert().

5.10.3. Побитовые операции над недвоичными изображениями

Побитовые операции также выполняются над изображениями в оттенках серого и цветными. Там они наиболее полезны, когда изображение содержит двоичноподобный контент – кадр в оттенках серого, чьи пиксели все равны 0 или 255, кадр RGB565 только с полностью черными и полностью белыми пикселями – где И, ИЛИ и исключающее ИЛИ дают те же комбинации, что и на настоящем двоичном изображении. Для изображений, охватывающих весь диапазон значений, арифметические операции на предыдущей странице обычно подходят лучше.