Nano Hash - криптовалюты, майнинг, программирование

Проверка изображений на равенство с помощью ImageMagick

Есть ли функция предиката равенства в библиотеке ImageMagick? Я хочу сравнить два изображения и выяснить, одинаковы ли они (все цвета пикселей одинаковы) или имеют какие-либо различия.

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


Ответы:


1

ImageMagick предоставляет функцию compare для правильного сравнения изображений.

Проверка контрольной суммы md5 двух изображений не является правильным подходом, поскольку некоторые форматы изображений (например, PNG и JPEG с EXIF) содержат дату и время создания файла (см. пример 1) ниже, а некоторые файлы можно визуально идентичны, но внутренне представлены совершенно по-разному (см. пример 2) или имеют разную разрядность (см. пример 3).

Пример 1

# Create two identical images (100x100 pixels, bright red) but with different file contents
convert -size 100x100 xc:red r1.png
convert -size 100x100 xc:red r2.png

# MD5 checksum them
md5 r?.png
MD5 (r1.png) = 9f6d612615efd88c3fd8521d717e9811
MD5 (r2.png) = 996911bec0e0da75af46a1e78c052998      # Mmmm different

# Ask IM to tell us absolute error between the two (number of differing pixels)
compare -metric AE r1.png r2.png null:
0                                                    # No difference - that's better

Почему эти два отличаются в MD5? Потому что в них дата...

identify -verbose r[12].png | grep -i date
date:create: 2015-03-03T14:57:26+00:00
date:modify: 2015-03-03T14:57:26+00:00
date:create: 2015-03-03T14:57:43+00:00
date:modify: 2015-03-03T14:57:43+00:00

Пример 2

# Create PNG and identical GIF
convert -size 100x100 xc:red r.png
convert -size 100x100 xc:red r.gif

# Compare with MD5 sums
md5 r.png r.gif
MD5 (r.png) = 692ef06b62a15b799d5dc549b0dd3737
MD5 (r.gif) = 549feea78dc438924fbb3e0ef97dc0b3         # Ooops

# Compare properly
compare -metric AE r.gif r.png null:
0                                                      # Identical

Пример 3

# Create 8-bit PNG and 16-bit PNG
convert -size 100x100 xc:red PNG8:8.png
convert -size 100x100 xc:red PNG48:48.png

# MD5 sum them
md5 8.png 48.png
MD5 (8.png) = eb3fc9a06e1632c3b41ebb986b81a816
MD5 (48.png) = 32fdf1c30793a4fed941c91d27084e0a   # Ooops

# Let ImageMagick compare them
compare -metric AE 8.png 48.png  null:
0

Нечеткое сравнение изображений

Как намекает Курт, это также приводит к возможности проведения нечеткого сравнения изображений. Мы можем исследовать это следующим образом:

# Create a grey image, 100x100 and put some noise in it
convert -size 100x100 xc:gray +noise gaussian noise.png

введите здесь описание изображения

Теперь умножьте все пиксели на 1,01, чтобы сделать их на незаметный 1% ярче:

# Make pixels 1% brighter
convert noise.png -evaluate multiply 1.01 brighternoise.png

# ... and compare the statistics of the two images
identify -verbose *noise* | grep -E "^Image|mean"

Image: brighternoise.png
  mean: 127.235 (0.498959)       <--- The brighter image is, well, brighter
Image: noise.png
  mean: 126.175 (0.494805)

А теперь сравните их несколькими разными способами:

# Pixels may differ by up to 2% before being considered different
compare -fuzz 2% -metric AE noise.png brighternoise.png null:
0        # All pixel values within 2% between the 2 images

# Pixels may only differ by 0.5% before being considered different
compare -fuzz 0.5% -metric AE noise.png brighternoise.png null:
594      # 594 of the 10,000 pixels differ by more than 0.5%

# Calculate Root Mean Square Error (RMSE) to see how much pixels tend to differ
compare -metric RMSE noise.png brighternoise.png null:
278.96 (0.00425666)    # On average, the pixels differ by 0.4% - i.e. hardly at all
03.03.2015
  • Для тех, кто пытается это сделать 6 лет спустя: compare -metric MAE 8.png 48.png. Они изменили имена параметров в более новых версиях. 03.03.2021

  • 2

    Ответ Марка точен. Однако он забыл упомянуть, что compare также может возвращать «дельта-изображение», которое будет окрашивать любой пиксель с различиями в красный цвет, а идентичные пиксели будут белыми.

    # Create a PNG and a JPEG from the builtin 'wizard:' image:
    convert wizard: wizard.png
    convert wizard: wizard.jpg
    

    Теперь сравните два:

    compare wizard.png wizard.jpg delta.png
    

    Это «дельта.png»:

    delta.png

    Много различий между PNG и JPEG! Хорошо, это объясняется тем, что JPEG является форматом изображения с потерями...

    Как видите, у файла delta.png бледный фон. Если вам не нужен этот фон, а только красные/белые пиксели, измените команду compare:

    compare wizard.png wizard.jpg -compose src delta.png
    

    Кроме того, вы можете игнорировать такие различия, которые ниже определенного порога. Здесь пригодится параметр -fuzz N%.

    Вы хотите синие пиксели вместо красных? А желтые вместо белых? Ну вот:

    compare                  \
      -highlight-color blue  \
      -lowlight-color yellow \
      -fuzz 3%               \
       wizard.png            \
       wizard.jpg            \
       delta2.png
    

    delta2.png

    Вы хотите текстовое описание всех пикселей, которые отличаются соответствующими координатами? Здесь может подойти специальный выходной формат *.txt.

    Попробуй это:

    compare                  \
      -fuzz 6%               \
       wizard.png            \
       wizard.jpg            \
      -compose src           \
       delta3.txt
    

    Файл delta3.txt будет довольно большим, потому что он содержит одну строку на пиксель в этом формате:

    # ImageMagick pixel enumeration: 480,640,255,srgba
    0,0: (255,255,255,0.8)  #FFFFFFCC  srgba(255,255,255,0.8)
    1,0: (255,255,255,0.8)  #FFFFFFCC  srgba(255,255,255,0.8)
    2,0: (255,255,255,0.8)  #FFFFFFCC  srgba(255,255,255,0.8)
    [....]
    77,80: (241,0,30,0.8)  #F1001ECC  srgba(241,0,30,0.8)
    [....]
    

    В первом столбце указана пара (row,column) соответствующего пикселя (счет ведется с нуля, самый верхний и самый левый пиксель имеет адрес (0,0).

    Следующие три столбца возвращают соответствующий цвет пикселя в трех различных распространенных форматах записи.

    Кстати, ImageMagick может без проблем преобразовать файл delta3.txt обратно в реальное изображение:

    convert delta3.txt delta3.png
    

    Итак, чтобы получить все пиксели, которые отличаются (красные) в текстовый файл, вы можете сделать это:

    compare                  \
      -fuzz 6%               \
       wizard.png            \
       wizard.jpg            \
      -compose src           \
       txt:-                 \
    | grep -v '#FFFFFFCC' 
    

    Чтобы подсчитать количество разных пикселей:

    compare                  \
      -fuzz 6%               \
       wizard.png            \
       wizard.jpg            \
      -compose src           \
       txt:-                 \
    | grep -v '#FFFFFFCC'    \
    | wc -l
    

    С -fuzz 6% у меня 2269 разных пикселей. С -fuzz 0% я получаю 122474 разных пикселей. (Общее количество пикселей на этих изображениях было 307200.)

    03.03.2015
    Новые материалы

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

    Как написать эффективное резюме
    Предложения по дизайну и макету, чтобы представить себя профессионально Вам не позвонили на собеседование после того, как вы несколько раз подали заявку на работу своей мечты? У вас может..

    Частный метод Python: улучшение инкапсуляции и безопасности
    Введение Python — универсальный и мощный язык программирования, известный своей простотой и удобством использования. Одной из ключевых особенностей, отличающих Python от других языков, является..

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

    Работа с векторными символическими архитектурами, часть 4 (искусственный интеллект)
    Hyperseed: неконтролируемое обучение с векторными символическими архитектурами (arXiv) Автор: Евгений Осипов , Сачин Кахавала , Диланта Хапутантри , Тимал Кемпития , Дасвин Де Сильва ,..

    Понимание расстояния Вассерштейна: мощная метрика в машинном обучении
    В обширной области машинного обучения часто возникает необходимость сравнивать и измерять различия между распределениями вероятностей. Традиционные метрики расстояния, такие как евклидово..

    Обеспечение масштабируемости LLM: облачный анализ с помощью AWS Fargate и Copilot
    В динамичной области искусственного интеллекта все большее распространение получают модели больших языков (LLM). Они жизненно важны для различных приложений, таких как интеллектуальные..