Не используйте Flatten() — глобальный пул для CNN с помощью TensorFlow и Keras PlatoBlockchain Data Intelligence. Вертикальный поиск. Ай.

Не используйте Flatten () — глобальный пул для CNN с TensorFlow и Keras

Большинство практиков, впервые изучая архитектуру сверточной нейронной сети (CNN), узнают, что она состоит из трех основных сегментов:

  • Сверточные слои
  • Объединение слоев
  • Полносвязные слои

Большинство ресурсов имеют некоторые вариант этой сегментации, включая мою собственную книгу. Особенно онлайн — полносвязные слои относятся к выравнивающий слой и (обычно) несколько плотные слои.

Раньше это было нормой, и известные архитектуры, такие как VGGNets, использовали этот подход и заканчивались:

model = keras.Sequential([
    
    keras.layers.MaxPooling2D((2, 2), strides=(2, 2), padding='same'),
    keras.layers.Flatten(),
    keras.layers.Dropout(0.5),
    keras.layers.Dense(4096, activation='relu'), 
    keras.layers.Dropout(0.5),
    keras.layers.Dense(4096, activation='relu'),
    keras.layers.Dense(n_classes, activation='softmax')
])

Хотя по какой-то причине часто забывают, что VGGNet была практически последней архитектурой, использовавшей этот подход, из-за создаваемого им явного вычислительного узкого места. Как только ResNets были опубликованы всего через год после VGGNets (и 7 лет назад), все основные архитектуры заканчивали свои определения моделей следующим образом:

model = keras.Sequential([
    
    keras.layers.GlobalAveragePooling2D(),
    keras.layers.Dense(n_classes, activation='softmax')
])

Сглаживание в CNN существует уже 7 лет. 7 лет! И мало кто говорит о разрушительном влиянии, которое это оказывает как на ваш учебный процесс, так и на вычислительные ресурсы, которые вы используете.

Глобальное среднее объединение предпочтительнее во многих учетных записях, чем выравнивание. Если вы создаете прототип небольшой CNN — используйте Global Pooling. Если вы обучаете кого-то CNN — используйте Global Pooling. Если вы делаете MVP — используйте Global Pooling. Используйте сглаживающие слои для других случаев использования, где они действительно необходимы.

Практический пример — выравнивание и глобальное объединение

Global Pooling объединяет все карты объектов в одну, объединяя всю соответствующую информацию в одну карту, которую можно легко понять с помощью одного плотного слоя классификации вместо нескольких слоев. Обычно он применяется как средний пул (GlobalAveragePooling2D) или максимальное объединение (GlobalMaxPooling2D) и может также работать для ввода 1D и 3D.

Вместо выравнивания карты объектов, такой как (7, 7, 32) в вектор длиной 1536 и обучить один или несколько слоев различать шаблоны из этого длинного вектора: мы можем сжать его в (7, 7) вектор и классифицировать прямо оттуда. Это так просто!

Обратите внимание, что слои узких мест для таких сетей, как ResNet, насчитывают десятки тысяч функций, а не просто 1536. При выравнивании вы пытаете свою сеть учиться на векторах странной формы очень неэффективным способом. Представьте, что 2D-изображение разрезается на каждую строку пикселей, а затем объединяется в плоский вектор. Два пикселя, которые раньше находились на расстоянии 0 пикселей друг от друга по вертикали, не feature_map_width пикселей по горизонтали! Хотя это может не иметь большого значения для алгоритма классификации, который способствует пространственной инвариантности, это даже концептуально не годится для других приложений компьютерного зрения.

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

model = keras.Sequential([
    keras.layers.Input(shape=(224, 224, 3)),
    keras.layers.Conv2D(32, (3, 3), activation='relu'),
    keras.layers.Conv2D(32, (3, 3), activation='relu'),
    keras.layers.MaxPooling2D((2, 2), (2, 2)),
    keras.layers.BatchNormalization(),
    keras.layers.Conv2D(64, (3, 3), activation='relu'),
    keras.layers.Conv2D(64, (3, 3), activation='relu'),
    keras.layers.MaxPooling2D((2, 2), (2, 2)),
    keras.layers.BatchNormalization(),
    keras.layers.Flatten(),
    keras.layers.Dropout(0.3),
    keras.layers.Dense(64, activation='relu'),
    keras.layers.Dense(32, activation='relu'),
    keras.layers.Dense(10, activation='softmax')
])
model.summary()

Как выглядит резюме?

...                                                              
 dense_6 (Dense)             (None, 10)                330       
                                                                 
=================================================================
Total params: 11,574,090
Trainable params: 11,573,898
Non-trainable params: 192
_________________________________________________________________

11.5 млн параметров для игрушечной сети — и наблюдайте, как параметры увеличиваются при увеличении входных данных. 11.5 млн параметров. EfficientNets, одна из самых эффективных сетей, когда-либо разработанных, работает с параметрами ~ 6M, и ее нельзя сравнивать с этой простой моделью с точки зрения фактической производительности и способности учиться на основе данных.

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

Углубление со слоями должно заключаться в извлечении более значимых нелинейных отношений между точками данных, а не в уменьшении размера входных данных для соответствия выравнивающему слою.

Вот сеть с глобальным пулом:

model = keras.Sequential([
    keras.layers.Input(shape=(224, 224, 3)),
    keras.layers.Conv2D(32, (3, 3), activation='relu'),
    keras.layers.Conv2D(32, (3, 3), activation='relu'),
    keras.layers.MaxPooling2D((2, 2), (2, 2)),
    keras.layers.BatchNormalization(),
    keras.layers.Conv2D(64, (3, 3), activation='relu'),
    keras.layers.Conv2D(64, (3, 3), activation='relu'),
    keras.layers.MaxPooling2D((2, 2), (2, 2)),
    keras.layers.BatchNormalization(),
    keras.layers.GlobalAveragePooling2D(),
    keras.layers.Dropout(0.3),
    keras.layers.Dense(10, activation='softmax')
])

model.summary()

Резюме?

 dense_8 (Dense)             (None, 10)                650       
                                                                 
=================================================================
Total params: 66,602
Trainable params: 66,410
Non-trainable params: 192
_________________________________________________________________

Намного лучше! Если мы углубимся в эту модель, количество параметров увеличится, и мы сможем зафиксировать более сложные закономерности данных с помощью новых слоев. Однако, если сделать это наивно, возникнут те же проблемы, которые связаны с VGGNets.

Двигаемся дальше — ручной комплексный проект

Ваша любознательная натура заставляет вас идти дальше? Рекомендуем ознакомиться с нашим Управляемый проект: «Сверточные нейронные сети — помимо базовых архитектур».

Ознакомьтесь с нашим практическим руководством по изучению Git с рекомендациями, принятыми в отрасли стандартами и прилагаемой памяткой. Перестаньте гуглить команды Git и на самом деле изучить это!

Я возьму вас в путешествие во времени — с 1998 по 2022 год, выделив определяющие архитектуры, разработанные на протяжении многих лет, что сделало их уникальными, каковы их недостатки, и реализовал примечательные из них с нуля. Нет ничего лучше, чем немного грязи на руках, когда дело доходит до них.

Вы можете водить машину, не зная, имеет ли двигатель 4 или 8 цилиндров и каково расположение клапанов в двигателе. Однако если вы хотите спроектировать и оценить движок (модель компьютерного зрения), вам нужно пойти немного глубже. Даже если вы не хотите тратить время на проектирование архитектур и вместо этого хотите создавать продукты, а это то, что хочется делать больше всего, вы найдете важную информацию в этом уроке. Вы узнаете, почему использование устаревших архитектур, таких как VGGNet, повредит вашему продукту и производительности, и почему вам следует пропустить их, если вы создаете что-то современное, и вы узнаете, какие архитектуры вы можете использовать для решения практических задач, а какие нет. плюсы и минусы есть у каждого.

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

Ты не нужно поискать в Google архитектуры и их реализации — обычно они очень четко объясняются в документах, а такие фреймворки, как Keras, делают эти реализации проще, чем когда-либо. Ключевой вывод этого управляемого проекта — научить вас находить, читать, реализовывать и понимать архитектуры и документы. Ни один ресурс в мире не сможет угнаться за всеми новейшими разработками. Я включил сюда самые свежие статьи, но через несколько месяцев появятся новые, и это неизбежно. Знание того, где найти надежные реализации, сравнить их с документами и настроить их, может дать вам конкурентное преимущество, необходимое для многих продуктов компьютерного зрения, которые вы, возможно, захотите создать.

Заключение

В этом кратком руководстве мы рассмотрели альтернативу выравниванию в архитектуре CNN. Хотя и краткое — руководство посвящено распространенной проблеме при разработке прототипов или MVP и советует вам использовать лучшую альтернативу сглаживанию.

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

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

Отметка времени:

Больше от Стекабьюс