Глубокое обучение нейронные сети: Глубокое обучение (Deep Learning): краткий туториал

Содержание

почему глубокие нейросети так сложно обучать? / Хабр

Представьте, что вы – инженер, и вас попросили разработать компьютер с нуля. Как-то раз вы сидите в офисе, изо всех сил проектируете логические контуры, распределяете вентили AND, OR, и так далее,- и вдруг входит ваш босс и сообщает вам плохие новости. Клиент только что решил добавить неожиданное требование к проекту: схема работы всего компьютера должна иметь не более двух слоёв:

Вы поражены, и говорите боссу: «Да клиент спятил!»

Босс отвечает: «Я тоже так думаю. Но клиент должен получить то, что хочет».


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

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

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

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

Поэтому глубокие схемы облегчают процесс проектирования. Но они помогают не только в проектировании. Есть математические доказательства того, что для вычисления некоторых функций в очень неглубоких схемах требуется использовать экспоненциально большее количество элементов, чем в глубоких. К примеру, есть знаменитая серия научных работ 1980-х годов, где показано, что вычисление чётности набора битов требует экспоненциально большего количества вентилей с неглубокой схемой. С другой стороны, при использовании глубоких схем легче вычислять чётность при помощи небольшой схемы: вы просто вычисляете чётность пар битов, а потом используете результат для подсчёта чётности пар пар битов, и так далее, быстро приходя к общей чётности. Поэтому глубокие схемы могут быть гораздо более мощными, чем неглубокие.

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

Эти простые сети оказались весьма полезными: в предыдущих главах мы использовали такие сети для классификации рукописных чисел с точностью, превышающей 98%! Тем не менее, интуитивно понятно, что сети с большим количеством скрытых слоёв будут гораздо более мощными:

Такие сети могут использовать промежуточные слои для создания множества уровней абстракции, как в случае с нашими булевскими схемами. К примеру, в случае распознавания образов, нейроны первого слоя могут научиться распознавать грани, нейроны второго слоя – более сложные формы, допустим, треугольники или прямоугольники, созданные из граней. Затем третий слой сможет распознавать ещё более сложные формы. И так далее. Вероятно, эти многие слои абстракции дадут глубоким сетям убедительное преимущество в решении задач по распознаванию сложных закономерностей. Более того, как и в случае со схемами, существуют теоретические результаты, подтверждающие, что глубокие сети по сути своей имеют больше возможностей, чем неглубокие.

Как нам обучать подобные глубокие нейросети (ГНС)? В данной главе мы попробуем обучить ГНС используя нашу рабочую лошадку среди обучающих алгоритмов – стохастический градиентный спуск с обратным распространением. Однако мы столкнёмся с проблемой – наши ГНС не будут работать сильно лучше (если вообще превзойдут), чем неглубокие.

Эта неудача кажется странной в свете дискуссии, приведённой выше. Но вместо того, чтобы махнуть на ГНС рукой, мы углубимся в проблему и попытаемся понять, почему ГНС тяжело обучать. Когда мы поближе познакомимся с вопросом, мы обнаружим, что разные слои в ГНС обучаются с крайне разными скоростями. В частности, когда последние слои сети обучаются хорошо, первые часто застревают во время обучения, и почти ничему не обучаются. И дело не в простом невезении. Мы обнаружим фундаментальные причины для замедления обучения, которые связаны с использованием техник обучения на основе градиента.

Зарывшись в эту проблему поглубже, мы узнаем, что может происходит и обратное явление: ранние слои могут обучаться хорошо, а более поздние — застревать. На самом деле, мы обнаружим внутреннюю нестабильность, связанную с обучением градиентным спуском в глубоких многослойных НС. И из-за этой нестабильности либо ранние, либо поздние слои часто застревают при обучении.

Всё это звучит довольно неприятно. Но погрузившись в эти трудности, мы можем начать разрабатывать идеи о том, что нужно сделать для эффективного обучения ГНС. Поэтому эти исследования станут хорошей подготовкой к следующей главе, где мы будем использовать глубокое обучение для подхода к задачам распознавания изображений.

Проблема исчезающего градиента

Так что же идёт не так, когда мы пытаемся обучить глубокую сеть?

Чтобы ответить на этот вопрос, вернёмся к сети, содержащей всего один скрытый слой. Как обычно, мы будем использовать задачу классификации цифр MNIST в качестве песочницы для обучения и экспериментов.

Если хотите повторять все эти действия на компьютере, у вас должны быть установлены Python 2.7, библиотека Numpy, и копия кода, которую можно взять с репозитория:

git clone https://github.com/mnielsen/neural-networks-and-deep-learning.git

Можно обойтись и без git, просто скачав данные и код. Перейдите в подкаталог src и из оболочки python загрузите данные MNIST:

>>> import mnist_loader
>>> training_data, validation_data, test_data = \
... mnist_loader.load_data_wrapper()

Настраиваем сеть:

>>> import network2
>>> net = network2.Network([784, 30, 10])

У такой сети есть 784 нейрона во входном слое, соответствующие 28×28=784 пикселям входного изображения. Мы используем 30 скрытых нейронов и 10 выходных, соответствующих десяти возможным вариантам классификации цифр MNIST (‘0’, ‘1’, ‘2’, …, ‘9’).

Попробуем обучать нашу сеть в течение 30 целых эпох с использованием мини-пакетов из 10 обучающих примеров за раз, скорость обучения η=0,1 и параметр регуляризации λ=5,0. Во время обучения мы будем отслеживать точность классификации через validation_data:

>>> net.SGD(training_data, 30, 10, 0.1, lmbda=5.0, 
... evaluation_data=validation_data, monitor_evaluation_accuracy=True)

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

Давайте добавим ещё один скрытый слой, также содержащий 30 нейронов, и попытаемся обучить сеть с теми же гиперпараметрами:

>>> net = network2.Network([784, 30, 30, 10])
>>> net.SGD(training_data, 30, 10, 0.1, lmbda=5.0, 
... evaluation_data=validation_data, monitor_evaluation_accuracy=True)

Точность классификации улучшается до 96,90%. Это вдохновляет – небольшое увеличение глубины помогает. Давайте добавим ещё один скрытый слой из 30 нейронов:

>>> net = network2.Network([784, 30, 30, 30, 10])
>>> net.SGD(training_data, 30, 10, 0.1, lmbda=5.0, 
... evaluation_data=validation_data, monitor_evaluation_accuracy=True)

Это никак не помогло. Результат даже упал до 96,57%, значения, близкого к первоначальной неглубокой сети. А если мы добавим ещё один скрытый слой:

>>> net = network2.Network([784, 30, 30, 30, 30, 10])
>>> net.SGD(training_data, 30, 10, 0.1, lmbda=5.0, 
... evaluation_data=validation_data, monitor_evaluation_accuracy=True)

Тогда точность классификации опять упадёт, уже до 96,53%. Статистически это падение, вероятно, незначительно, однако и ничего хорошего в этом нет.

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

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

Чтобы понять, что пошло не так, давайте визуализируем процесс обучения сети. Ниже я построил часть сети [784,30,30,10], в которой есть два скрытых слоя, в каждом из которых по 30 скрытых нейронов. На диаграмме у каждого нейрона есть полоска, обозначающая скорость изменения в процессе обучения сети. Большая полоска значит, что веса и смещения нейрона меняются быстро, а маленькая – что они меняются медленно. Точнее, полоска обозначает градиент ∂C/∂b нейрона, то есть, скорость изменения стоимости по отношению к смещению. В главе 2 мы увидели, что эта величина градиента контролирует не только скорость изменения смещения в процессе обучения, но и скорость изменения входных весов нейрона. Не волнуйтесь, если вы не можете вспомнить эти детали: надо просто иметь в виду, что эти полоски обозначают, насколько быстро меняются веса и смещения нейронов в процессе обучения сети.

Для упрощения диаграммы я нарисовал только шесть верхних нейронов в двух скрытых слоях. Я опустил входящие нейроны, поскольку у них нет весов или смещений. Я опустил и выходные нейроны, поскольку мы сравниваем два слоя, и имеет смысл сравнивать слои с одинаковым количеством нейронов. Диаграмма построена при помощи программы generate_gradient.py в самом начале обучения, то есть, сразу после того, как сеть была инициализирована.

Сеть была инициализирована случайно, поэтому такое разнообразие в скорости обучения нейронов неудивительно. Однако сразу же бросается в глаза, что во втором скрытом слое полоски в основном гораздо больше, чем в первом. В итоге нейроны во втором слое будут учиться гораздо быстрее, чем в первом. Совпадение ли это, или нейроны во втором слое, вероятно, в общем будут обучаться быстрее нейронов в первом?

Чтобы узнать точно, хорошо будет иметь общий способ сравнения скорости обучения в первом и втором скрытых слоях. Для этого давайте обозначим градиент как δlj = ∂C/∂blj, то есть, как градиент нейрона №j в слое №l. Во второй главе мы называли это «ошибкой», но здесь я будут неформально называть это «градиентом». Неформально – поскольку в эту величину не входят явно частные производные стоимости по весам, ∂C/∂w. Градиент δ1 можно представлять себе как вектор, чьи элементы определяют, насколько быстро обучается первый скрытый слой, а δ2 — как вектор, чьи элементы определяют, насколько быстро обучается второй скрытый слой. Длины этих векторов мы используем, как приблизительные оценки скорости обучения слоёв. То есть, к примеру, длина || δ1 || измеряет скорость обучения первого скрытого слоя, а длина || δ2 || измеряет скорость обучения второго скрытого слоя.

С такими определениями и с той же конфигурацией, что указана выше, мы обнаружим, что || δ1 || = 0,07, а || δ2 || = 0,31. Это подтверждает наши подозрения: нейроны во втором скрытом слое обучаются гораздо быстрее, чем нейроны в первом скрытом слое.

Что будет, если мы добавим больше скрытых слоёв? С тремя скрытыми слоями в сети [784,30,30,30,10] соответствующие скорости обучения составят 0,012, 0,060 и 0,283. Опять первые скрытые слои обучаются гораздо медленнее последних. Добавим ещё один скрытый слой с 30 нейронами. В данном случае соответствующие скорости обучения составят 0,003, 0,017, 0,070 и 0,285. Закономерность сохраняется: ранние слои обучаются медленнее поздних.

Мы изучали скорость обучения в самом начале – сразу после инициализации сети. Как же меняется эта скорость по мере обучения? Давайте вернёмся и посмотрим на сеть с двумя скрытыми слоями. Скорость обучения меняется в ней так:

Для получения этих результатов я использовал пакетный градиентный спуск с 1000 обучающих изображений и обучение в течение 500 эпох. Это немного отличается от наших обычных процедур – я не использовал мини-пакеты и взял всего 1000 обучающих изображений, вместо полного набора из 50 000 штук. Я не пытаюсь хитрить и обманывать вас, но оказывается, что использование стохастического градиентного спуска с мини-пакетами привносит в результаты гораздо больше шума (но если усреднять шум, то результаты получаются похожими). Используя выбранные мною параметры легко сгладить результаты, чтобы мы могли увидеть, что происходит.

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

Что насчёт более сложных сетей? Вот результаты похожего эксперимента, но уже с сетью с тремя скрытыми слоями [784,30,30,30,10]:

И снова первые скрытые слои обучаются гораздо медленнее последних. Наконец, попробуем добавить четвёртый скрытый слой (сеть [784,30,30,30,30,10]), и посмотрим, что произойдёт при её обучении:

И снова первые скрытые слои обучаются гораздо медленнее последних. В данном случае первый скрытый слой обучается примерно в 100 раз медленнее последнего. Неудивительно, что у нас были такие проблемы с обучением этих сетей!

Мы провели важное наблюдение: по крайней мере, в некоторых ГНС градиент уменьшается при движении в обратную сторону по скрытым слоям. То есть, нейроны в первых слоях обучаются гораздо медленнее нейронов в последних. И хотя мы наблюдали этот эффект всего в одной сети, существуют фундаментальные причины того, почему это происходит во многих НС. Это явление известно под названием «проблемы исчезающего градиента» (см. работы 1, 2).

Почему возникает проблема исчезающего градиента? Есть ли способы её избежать? Как нам быть с ней при обучении ГНС? На самом деле вскоре мы узнаем, что она не является неизбежной, хотя альтернатива ей и не выглядит очень уж привлекательное: иногда в первых слоях градиент оказывается гораздо больше! Это уже проблема взрывного роста градиента, и в ней не больше хорошего, чем в проблеме исчезающего градиента. В целом оказывается, что градиент в ГНС нестабилен, и склонен либо к взрывному росту, либо к исчезновению в первых слоях. Эта нестабильность является фундаментальной проблемой для градиентного обучения ГНС. Это то, что нам нужно понять, и по возможности как-то решить.

Одна из реакций на исчезающий (или нестабильный) градиент – подумать, а является ли это на самом деле серьёзной проблемой? Ненадолго отвлечёмся от НС, и представим, что мы пытаемся численным образом минимизировать функцию f(x) от одного переменного. Разве не было бы здорово, если бы производная f′(x) была малой? Не означало бы это, что мы уже близки к экстремуму? И точно так же, не означает ли небольшой градиент в первых слоях ГНС, что нам уже не нужно сильно подстраивать веса и смещения?

Конечно же, нет. Вспомним, что мы случайным образом инициализировали веса и смещения сети. Крайне маловероятно, что наши изначальные веса и смешения хорошо справятся с тем, чего мы хотим от нашей сети. В качестве конкретного примера рассмотрим первый слой весов в сети [784,30,30,30,10], классифицирующей цифры MNIST. Случайная инициализация означает, что первый слой выбрасывает большую часть информации о входящем изображении. Даже если бы более поздние слои были тщательно обучены, им бы было чрезвычайно сложно определять входящее сообщение, просто из-за недостатка информации. Поэтому совершенно невозможно представить, что первому слою просто не нужно обучаться. Если мы собираемся обучать ГНС, нам надо понять, как решать проблему исчезающего градиента.

Что вызывает проблему исчезающего градиента? Нестабильные градиенты в ГНС

Чтобы понять, как появляется проблема исчезающего градиента, рассмотрим простейшую НС: всего с одним нейроном в каждом слое. Вот сеть с тремя скрытыми слоями:

Здесь w1, w2,… – это веса, b1, b2,… – смещения, С – некая функция стоимости. Просто для напоминания скажу, что выход aj с нейрона №j равен σ(zj), где σ — обычная сигмоидная функция активации, а zj = wjaj−1+bj — взвешенный вход нейрона. Функцию стоимости я изобразил в конце, чтобы подчеркнуть, что стоимость является функцией от выхода сети, a4: если реальный выход близок к желаемому, тогда стоимость будет маленькой, а если далёк – то большой.

Изучим градиент ∂C/∂b1, связанный с первым скрытым нейроном. Найдём выражение для ∂C/∂b1 и, изучив его, поймём, почему возникает проблема исчезающего градиента.

Начнём с демонстрации выражения для ∂C/∂b1. Выглядит неприступно, но на самом деле структура его проста, и я скоро опишу её. Вот это выражение (пока игнорируйте саму сеть и отметьте, что σ′ — просто производная от функции σ):

Структура выражения такова: для каждого нейрона в сети имеется член умножения σ′(zj), для каждого веса имеется wj, и ещё есть последний член, ∂C/∂a4, соответствующий функции стоимости. Заметьте, что я разместил соответствующие члены над соответствующими частями сети. Поэтому сама сеть является мнемоническим правилом для выражения.

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

Представьте, что мы внесли небольшое изменение Δb1 в смещение b1. Это отправит серию каскадных изменений по всей остальной сети. Сначала это заставит измениться выход первого скрытого нейрона Δa1. Это, в свою очередь, заставить измениться Δz2 во взвешенном входе на второй скрытый нейрон. Затем произойдёт изменение Δa2 в выходе второго скрытого нейрона. И так далее, вплоть до изменения ΔC в стоимости выхода. Получится, что:

Это говорит о том, что мы можем вывести выражение для градиента ∂C/∂b1, тщательно отслеживая влияние каждого шага в этом каскаде.

Для этого подумаем, как Δb1 заставляет меняться выход a1 первого скрытого нейрона. Имеем a1 = σ(z1) = σ(w1a0+b1), поэтому

Член σ′(z1) должен выглядеть знакомым: это первый член нашего выражения для градиента ∂C/∂b1. Интуитивно понятно, что он превращает изменение смещения Δb1 в изменение Δa1 выходной активации. Изменение Δa1 в свою очередь вызывает изменение взвешенного входа z2 = w2a1+b2 второго скрытого нейрона:

Комбинируя выражения для Δz2 и Δa1, мы видим, как изменение смещения b1 распространяется вдоль сети и влияет на z2:

И это тоже должно быть знакомо: это два первых члена в нашем заявленном выражении для градиента ∂C/∂b1.

Так можно продолжать и далее, отслеживая, как изменения распространяются по остальной сети. На каждом нейроне мы подбираем член σ′(zj), и через каждый вес мы подбираем член wj. В итоге получается выражение, связывающее конечное изменение ΔC функции стоимости с начальным изменением Δb1 смещения:

Разделив его на Δb1, мы действительно получим нужное выражение для градиента:

Почему возникает проблема исчезающего градиента?

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

Кроме последнего члена, это выражение есть произведение членов вида wjσ′(zj). Чтобы понять, как ведёт себя каждый из них, посмотрим на график функции σ′:

График достигает максимума в точке σ′(0)=1/4. Если мы используем стандартный подход к инициализации весов сети, то мы выбираем веса с использованием распределения Гаусса, то есть, среднеквадратичным нулём и стандартным отклонением 1. Поэтому обычно веса будут удовлетворять неравенству |wj|<1. Сопоставив все эти наблюдения, увидим, что члены wjσ′(zj) обычно будут удовлетворять неравенству |wjσ′(zj)|<1/4. А если мы возьмём произведение множества таких членов, то оно будет экспоненциально уменьшаться: чем больше членов, тем меньше произведение. Начинает походить на возможную разгадку проблемы исчезающего градиента.

Чтобы записать это более точно, сравним выражение для ∂C/∂b1 с выражением градиента относительно следующего смещения, допустим, ∂C/∂b3. Конечно, мы не записывали подробное выражение для ∂C/∂b3, но оно следует тем же закономерностям, что описаны выше для ∂C/∂b1. И вот сравнение двух выражений:

У них есть несколько общих членов. Однако в градиент ∂C/∂b1 входит два дополнительных члена, каждый из которых имеет вид wjσ′(zj). Как мы видели, такие члены обычно не превышают 1/4. Поэтому градиент ∂C/∂b1 обычно будет в 16 (или больше) раз меньше, чем ∂C/∂b3. И это основная причина возникновения проблемы исчезающего градиента.

Конечно, это не точное, а неформальное доказательство возникновения проблемы. Существуют несколько оговорок. В частности, можно заинтересоваться тем, будут ли во время обучения расти веса wj. Если это произойдёт, члены wjσ′(zj) в произведении уже не будут удовлетворять неравенству |wjσ′(zj)|<1/4. И если они окажутся достаточно большими, больше 1, то у нас уже не будет проблемы исчезающего градиента. Вместо этого градиент будет экспоненциально расти при обратном движении через слои. И вместо проблемы исчезающего градиента мы получим проблему взрывного роста градиента.

Проблема взрывного роста градиента

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

Для взрывного роста градиента нужно сделать два шага. Сначала мы выберем большие веса во всей сети, допустим, w1=w2=w3=w4=100. Потом мы выберем такие смещения, чтобы члены σ′(zj) были не слишком маленькими. И это довольно легко сделать: нам нужно лишь выбрать такие смещения, чтобы взвешенный вход каждого нейрона был zj=0 (и тогда σ′(zj)=1/4). Поэтому, к примеру, нам нужно, чтобы z1=w1a0+b1=0. Этого можно достичь, назначив b1=−100∗a0. Ту же идею можно использовать и для выбора остальных смещений. В итоге мы увидим, что все члены wjσ′(zj) окажутся равными 100∗14=25. И тогда у нас получится взрывной рост градиента.

Проблема нестабильного градиента

Фундаментальная проблема заключается не в проблеме исчезающего градиента или взрывном росте градиента. Она в том, что градиент в первых слоях является произведением членов из всех остальных слоёв. И когда слоёв много, ситуация по сути становится нестабильной. И единственный способ, которым все слои смогут обучаться с примерно одной скоростью – это выбрать такие члены произведения, которые будут балансировать друг друга. И при отсутствии некоего механизма или причины для такой балансировки маловероятно, что это произойдёт случайно. Короче говоря, реальная проблема в том, что НС страдают от проблемы нестабильного градиента. И в итоге, если мы будем использовать стандартные обучающие техники на основе градиента, разные слои сети будут обучаться с ужасно разными скоростями.

Упражнение

  • В нашем обсуждении проблемы исчезающего градиента мы использовали тот факт, что |σ′(z)|<1/4. Допустим, мы используем другую функцию активации, производная которой может быть гораздо больше. Поможет ли это нам решить проблему нестабильного градиента?

Преобладание проблемы исчезающего градиента

Мы видели, что градиент может исчезать или расти взрывными темпами в первых слоях глубокой сети. На самом деле при использовании сигмоидных нейронов градиент обычно будет исчезать. Чтобы понять, почему, снова рассмотрим выражение |wσ′(z)|. Чтобы избежать проблемы исчезающего градиента, нам нужно, чтобы |wσ′(z)|≥1. Вы можете решить, что этого легко достичь при очень больших значениях w. Однако на самом деле это не так просто. Причина в том, что член σ′(z) тоже зависит от w: σ′(z)=σ′(wa+b), где a – это входная активация. И если мы сделаем w большим, нам надо постараться, чтобы параллельно не сделать σ′(wa+b) маленьким. А это оказывается серьёзным ограничением. Причина в том, что когда мы делаем w большим, мы делаем wa+b очень большим. Если посмотреть на график σ′, видно, что это приводит нас к «крыльям» функции σ′, где она принимает очень малые значения. И единственный способ избежать этого – удерживать входящую активацию в достаточно узком диапазоне значений. Иногда это происходит случайно. Но чаще этого не происходит. Поэтому в общем случае у нас возникает проблема исчезающего градиента.

Задачи

  • Рассмотрим результат умножения |wσ′(wa+b)|. Допустим, |wσ′(wa+b)|≥1. Покажите, что это может произойти, только если |w|≥4.
  • Предполагая, что |w|≥4, рассмотрите набор входных активаций, для которых |wσ′(wa+b)|≥1.
  • Покажите, что набор активаций, удовлетворяющий этому ограничению, может находиться в интервале с шириной не более

  • Покажите численно, что это выражение сильнее всего ограничивает ширину диапазона при |w|≈6.9, и в этой точке принимает значение ≈0,45. Поэтому, даже если всё будет подобрано идеально, у нас всё равно будет достаточно узкий диапазон входных активаций, способных избежать проблемы исчезающего градиента.
  • Тождественный нейрон. Рассмотрим нейрон с одним входом x, соответствующим весом w1, смещением b и весом w2 на выходе. Покажите, что правильно выбрав веса и смещение, можно гарантировать, что w2σ(w1x+b)≈x for x∈[0,1]. И тогда такой нейрон можно использовать как тождественный, то есть такой, выход которого примерно равен входу (с точностью масштабирования на множитель веса). Подсказка: Полезно переписать x=1/2+Δ, предположить, что w1 мало, и использовать разложение w1Δ в ряд Тейлора.

Нестабильность градиентов в более сложных сетях

Мы изучали игрушечные сети всего лишь с одним нейроном в каждом скрытом слое. Что насчёт более сложных глубоких сетей, у которых в каждом скрытом слое есть много нейронов?

На самом деле, в таких сетях происходит примерно то же самое. Ранее в главе про обратное распространение мы видели, что градиент в слое №l сети с L слоями задаётся, как:

Здесь Σ′(zl) – диагональная матрица, чьи элементы – это значения σ′(z) для взвешенных входов слоя №l. wl — это матрицы весов для разных слоёв. А ∇aC – вектор частных производных C по выходным активациям.

Это выражение гораздо сложнее случая с одним нейроном. И всё же, если приглядеться, его суть окажется весьма похожей, с кучей пар вида (wj)TΣ′(zj). Более того, у матриц Σ′(zj) по диагонали стоят небольшие значения, не больше 1/4. Если весовые матрицы wj будут не слишком крупными, каждый дополнительный член (wj)T Σ′(zl) склонен уменьшать градиентный вектор, что ведёт к исчезающему градиенту. В общем случае, большее количество членов перемножения ведёт к нестабильному градиенту, как в нашем предыдущем примере. На практике эмпирически обычно в сигмоидных сетях градиенты в первых слоях исчезают экспоненциально быстро. В итоге в этих слоях замедляется обучение. И замедление не является случайностью или неудобством: это фундаментальное следствие избранного нами подхода к обучению.

Другие препятствия на пути к глубокому обучению

В этой главе я сконцентрировался на исчезающих градиентах – и более общем случае нестабильных градиентов – в качестве препятствия на пути к глубокому обучению. На самом деле, нестабильные градиенты – всего лишь одно препятствие для развития ГО, пусть и важное, и фундаментальное. Значительная часть текущих исследований пытается лучше понять проблемы, которые могут возникнуть при обучении ГО. Я не буду подробно описывать все эти работы, однако хочу кратенько упомянуть парочку работ, чтобы дать вам представление о некоторых вопросах, задаваемых людьми.

В качестве первого примера в работе 2010 года было найдено свидетельство тому, что использование сигмоидных функций активации может привести к проблемам с обучением НС. В частности, было обнаружено свидетельство того, что использование сигмоид приведёт к тому, что активации последнего скрытого слоя будут во время обучения насыщаться в районе 0, что будет серьёзно замедлять обучение. Было предложено несколько альтернативных функций активации, не страдающих так сильно от проблемы насыщения (см. также ещё одну работу с обсуждением).

В качестве первого примера в работе 2013 года изучалось влияние на ГО как случайной инициализации весов, так и график импульсов в стохастическом градиентном спуске на основе импульса. В обоих случаях хороший выбор значительно влиял на возможность обучать ГНС.

Эти примеры говорят о том, что вопрос «Почему ГНС так сложно обучать?» очень сложный. В данной главе мы сконцентрировались на нестабильностях, связанных с градиентным обучением ГНС. Результаты двух предыдущих параграфов говорят о том, что роль играет ещё и выбор функции активации, способ инициализации весов и даже детали реализации обучения на основе градиентного спуска. И, естественно, важными будут выбор архитектуры сети и других гиперпараметров. Поэтому множество факторов может сыграть роль в затруднении обучения глубоких сетей, и вопрос понимания этих факторов является объектом текущих исследований. Но всё это кажется довольно мрачным и внушает пессимизм. Однако есть и хорошие новости – в следующей главе мы обернём всё в нашу пользу, и разработаем несколько подходов в ГО, которые до некоторой степени смогут преодолеть или обойти все эти проблемы.

Глубокое обучение: быстрый старт для разработчиков | GeekBrains

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

https://d2xzmw6cctk25h.cloudfront.net/post/1258/og_cover_image/f0092845782bef7fa816205c9e2aa3d4

Здравствуйте!

Глубокое обучение считается чем-то вроде rocket science: звучит круто, выглядит сложно и содержит всякую математику. На самом деле все не так сложно. Вот вам перевод руководства по глубокому обучению «Deep Learning for Developers: Tools You Can Use to Code Neural Networks on Day 1» от Эмиля Волнера.

Текущая волна интереса к глубокому обучению началась лет пять назад. Экспоненциальный рост мощности компьютеров и истории успеха стали тому причиной. Глубокое обучение — технология, управляющая автомобилями, побеждающая людей в играх Atari и диагностирующая рак.


Arif Wahid, Unsplash

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

Вам не нужна особая подготовка. Достаточно базового понимания Python, командной строки и Jupyter notebook.

Глубокое обучение — часть машинного обучения. Доказано, что это эффективный метод поиска паттернов в сырых данных, таких как звук или изображение. Скажем, вы хотите классифицировать картинки кошек и собак. Без специального программирования, сперва выделим границы изображения. Затем построим паттерны из набора изображений, и наконец выделим носы, хвосты и лапы. Так нейронная сеть в итоге классифицирует собак и кошек.

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

Основная логика

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

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

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

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

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

Мелкая искусственная нейронная сеть

Многие считают, что искусственные нейронные сети — цифровые копии нашего неокортекса. Это не так. Мы слишком мало знаем о собственном мозге, чтобы требовать такое. Это было источником вдохновения для Фрэнка Розенблатта, создателя нейронных сетей.

Поиграйтесь с симулятором нейронной сети пару часов, чтобы примерно почувствовать, как это работает. Мы начнем с создания простой нейронной сети, чтобы познакомиться с синтаксисом TFlearn. Классическая проблема для начала — оператор OR. Хотя нейронные сети лучше подходят для других типов данных, для начала сойдет и такой вариант, чтобы понять, как это вообще работает.

Все программы глубокого обучения следуют одной логике:

  • Сперва подключаем библиотеки, импортируем и очищаем данные. Все входные данные интерпретируются как числа, неважно, изображения это, звуки или данные с сенсоров.
  • Эти длинные списки чисел — входные данные для нашей сети.
  • Теперь описываем нейронную сеть.
  • Выбираем тип и количество слоев сети.
  • Идет процесс обучения.
  • Сеть ищет корреляцию между входными данными и выходными.
  • Финальный шаг выводит предсказание, полученное обученной сетью.

Вот код нашей сети.


# 1. Import library of functions
import tflearn
# 2. Logical OR operator / the data
OR = [[0., 0.], [0., 1.], [1., 0.], [1., 1.]]
Y_truth = [[0.], [1.], [1.], [1.]]
# 3. Building our neural network/layers of functions 
neural_net = tflearn.input_data(shape=[None, 2])
neural_net = tflearn.fully_connected(neural_net, 1, activation='sigmoid')
neural_net = tflearn.regression(neural_net, optimizer='sgd', learning_rate=2, loss='mean_square')
# 4. Train the neural network / Epochs
model = tflearn.DNN(neural_net)
model.fit(OR, Y_truth, n_epoch=2000, snapshot_epoch=False)
# 5. Testing final prediction
print("Testing OR operator")
print("0 or 0:", model.predict([[0., 0.]]))
print("0 or 1:", model.predict([[0., 1.]]))
print("1 or 0:", model.predict([[1., 0.]]))
print("1 or 1:", model.predict([[1., 1.]]))

Вывод программы:


Training Step: 2000  | total loss: 0.00072 | time: 0.002s
| SGD | epoch: 2000 | loss: 0.00072 -- iter: 4/4

Testing OR operator

0 or 0: [[ 0.04013482]]
0 or 1: [[ 0.97487926]]
1 or 0: [[ 0.97542077]]
1 or 1: [[ 0.99997282]]

Строка 1

Комментарии начинаются с #

Строка 2

Подключаем библиотеку TFlearn, она позволит нам использовать функции глубокого обучения из Google Tensorflow.

Строки 5–6

Данные из таблицы сохраняются в списки. Точка в конце каждого числа преобразует их в числа с плавающей точкой. Это повысит точность вычисления.

Строка 9

Инициализируем сеть и определяем форму входных данных. Каждый оператор OR идет парой, таким образом имея форму, равную 2. None — дефолтное значение, представляющее размер серии.

Строка 10

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

Вот материал, который более подробно раскроет суть строк 9 и 10: tflearn.org/layers/core

Строка 11

Применяем регрессию. Параметр optimizer выбирает алгоритм минимизации функции потерь. Параметр learning rate определяет, как быстро нужно модифицировать сеть, и параметр loss определяет, как вычислять ошибку.

Строка 14

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

Строка 15

Тренируем сеть и модель. Выбираем входные данные (OR) и эталонную метку (Y_truth). Параметр n_epoch определяет, сколько раз мы прогоним данные через сеть. snapshot_epoch=True определяет, нужно ли валидировать модель после каждого прогона.

Строки 18–22

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

Подробнее насчет строк 1422: tflearn.org/models/dnn

Вывод

Первый результат — комбинация [0.] & [0.], с вероятностью в 4% это true, и так далее. Выше можно увидеть, сколько обучений в итоге прошла модель. Поскольку данные помещаются в одну серию, это все равно что одна эпоха. Если данные слишком велики, чтобы поместиться в памяти, вам придется разбить их на части. loss — сумма ошибок по всем эпохам. SGD — стохастический градиентный спуск (Stochastic Gradient Descent), метод минимизации функции потерь. Iter показывает текущий кусок данных и общий размер данных.

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

Кривая потерь показывает количество ошибок на каждом шаге обучения. С Tensorboard вы можете визуально наблюдать за каждым экспериментом и развивать чувство того, какие параметры меняют обучение. Вот несколько вариаций изначального эксперимента, с которыми вы можете поиграться самостоятельно. Советую потратить несколько часов на то, чтобы освоиться с окружением и параметрами TFlearn.

Эксперименты:

  • Увеличьте количество обучений и эпох
  • Попробуйте поменять или добавить все возможные параметры к каждой функции, руководствуясь документацией: например, вместо  tflearn.fullyconnected(g, 1, activation=’sigmoid’) попробуйте tflearn.fullyconnected(g, 1, activation=’sigmoid’, bias=False)
  • Добавьте числа во входные данные
  • Поменяйте форму входных данных
  • Поменяйте функцию активации
  • Поменяйте метод градиентного спуска
  • Поменяйте подход к вычислению стоимости
  • Попробуйте AND и NOT операторы
  • Попробуйте XOR для тестирования выходных данных, например, поменяйте последний Y_truth с [1.] на [0.]
  • Попробуйте добавить еще уровень сети
  • Попробуйте добиться более быстрого обучения
  • Найдите способ добиться того, чтобы каждый шаг обучения был дольше 0.1 секунды

Начало работы

Python и Tensorflow — самая распространенная связка для глубокого обучения. TFlearn — фреймворк высокого уровня, построенный поверх Tensorflow. Другой распространенный фреймворк — Keras. У него больше возможностей, но я нахожу синтаксис TFlearn более простым и понятным. Оба фреймворка работают поверх Tensorflow.

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

Простейшее решение для облачной обработки на GPU — FloydHub. Если вы хотя бы немного умеете обращаться с командной строкой, у вас уйдет не больше пяти минут на запуск.

Установите floyd-cli, пользуясь документацией. Кроме того, у FloydHub есть чат в Intercom, на случай, если вы застряли на каком-то этапе. Давайте запустим вашу первую сеть в FloydHub, используя TFlearn, Jupyter Notebook, и Tensorboard. После установки и входа в FloydHub, скачайте необходимые файлы:


git clone https://github.com/emilwallner/Deep-Learning-101.git
cd Deep-Learning-101
floyd init 101

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


floyd init 101

Теперь вы готовы к запуску сети на FloydHub.

Команда запуска проекта принимает различные параметры. Сейчас наши действия таковы:

  • Примонтируем датасет к FloydHub, используя параметр —data emilwallner/datasets/cifar-10/1:data. Мы можем просмотреть датасет (и вообще большинство публичных датасетов) прямо на FloydHub.
  • Используем облачный GPU с параметром —gpu
  • Подключаем Tensorboard с параметром —tensorboard
  • Запускаем задачу в режиме Jupyter Notebook с параметром —mode jupyter

Окей, поехали:


floyd run --data emilwallner/datasets/cifar-10/1:data --gpu --tensorboard --mode jupyter

Как только команда инициализирует Jupyter в браузере, откройте файл с именем start-here.ipnyb. Это простая нейронная сеть для знакомства с синтаксисом TFlearn. Мы подробно разобрались с ней выше.

В меню выберите Kernel > Restart & Run All. Если вы увидите сообщение, значит все работает. Зайдите в проект на FloydHub, и там вы найдете ссылку на Tensorboard.

Глубокая нейронная сеть

Глубокая сеть — сеть с несколькими скрытыми слоями. Работа сверточных сетей подробно разбирается в руководствах:

Мы же сосредоточимся на высокоуровневых принципах, которые применимы к большинству сетей.

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

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

Регуляризация — процесс уменьшения переобучения путем забывания определенных сигналов из тренировочных данных. Чтобы лучше понять этот принцип, мы используем датасет CIFAR-10. Это 60 тысяч изображений в десяти категориях, таких как автомобили, грузовики и птицы. Цель — определить категории изображений.

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

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

Выбор количества слоев

Давайте посмотрим, как отличается сеть с одним и тремя наборами слоев. Каждый набор состоит из слоев свертки, подвыборки и соединительного слоя. Первые два эксперимента — experiment-0-few-layers.ipynb и experiment-0-three-layer-sets.ipynb.


# Convolutional network building
network = input_data(shape=[None, 32, 32, 3],
                     data_preprocessing=img_prep,
                     data_augmentation=img_aug)
# One set of layers
network = conv_2d(network, 32, 3, activation='relu')
network = max_pool_2d(network, 2)
network = fully_connected(network, 512, activation='relu')
network = fully_connected(network, 10, activation='softmax')
network = regression(network, optimizer='adam',
                     loss='categorical_crossentropy',
                     learning_rate=0.001)

Глядя на графики в Tensorboard, мы заметим, что сеть с одним набором примерно на 15% аккуратнее сети с несколькими наборами. Дело в том, что сеть с несколькими наборами недообучена.

Посмотрите на графики Accuracy и Accuracy/Validation. Наилучший подход в глубоком обучении — разделить датасет пополам, одну половину используя в обучении, а вторую для валидации. Так вы определите, как хорошо нейронная сеть справляется с предсказанием на новых данных, то есть с ее способностью к обобщению.

Как мы видим, точность тренировочных данных выше точности данных для валидации. Фоновый шум и детали мешают сети хорошо работать на новых данных.

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

Исключающие слои

Регуляризация исключением похожа на демократию: вместо использования нескольких мощных нейронов мы распределяем мощность по всей сети.

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


network = input_data(shape=[None, 32, 32, 3],
                        data_preprocessing=img_prep,
                        data_augmentation=img_aug)
network = conv_2d(network, 32, 3, activation='relu')
network = max_pool_2d(network, 2)
network = conv_2d(network, 64, 3, activation='relu')
network = conv_2d(network, 64, 3, activation='relu')
network = max_pool_2d(network, 2)
network = fully_connected(network, 512, activation='relu')
#The dropout layer
network = dropout(network, 0.5)
network = fully_connected(network, 10, activation='softmax')
network = regression(network, optimizer='adam',
                        loss='categorical_crossentropy',
                        learning_rate=0.001)

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

Второй популярный метод предотвращения переобучения — применение L1/L2 регуляторной функции на каждый слой.

L1 и L2 регуляризация

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


network = input_data(shape=[None, 32, 32, 3],
                        data_preprocessing=img_prep,
                        data_augmentation=img_aug)
network = conv_2d(network, 32, 3, activation='relu', regularizer='L2')
network = max_pool_2d(network, 2)
network = conv_2d(network, 64, 3, activation='relu', regularizer='L2')
network = conv_2d(network, 64, 3, activation='relu', regularizer='L2')
network = max_pool_2d(network, 2)
network = fully_connected(network, 512, activation='relu', regularizer='L2')
network = fully_connected(network, 10, activation='softmax')
network = regression(network, optimizer='adam',
                        loss='categorical_crossentropy',
                        learning_rate=0.001)

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

Нейронная сеть с регуляризацией показывает себя лучше сети без регуляризации.

Регуляторная функция L2 ограничивает влияние слишком сложных функций. Она вычисляет, как сильно каждая функция влияет на конечный результат, и вводит ограничивающие коэффициенты.

Размер серии

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


#Large batch size
model.fit(X, Y, 
          n_epoch=50, 
          shuffle=True, 
          validation_set=(X_test, Y_test), 
          show_metric=True, 
          batch_size=2000, 
          run_id='cifar_large_batch_size')

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

Большая серия сделает меньше шагов, но расход времени и памяти на каждый шаг больше.

Скорость обучения

Финальный эксперимент — сравнение сетей с малой, средней и высокой скоростью обучения.


#Large learning rate
network = regression(network, 
                     optimizer='adam',
                     loss='categorical_crossentropy',
                     learning_rate=0.01)

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

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

Когда вы закончите с экспериментами, не забудьте остановить инстанс на FloydHub, выбрав в меню Cancel.

Следующие шаги

В официальном репозитории TFlearn вы найдете примеры хороших сверточных сетей. Разберитесь с тем, как они устроены, и попробуйте улучшить свою сеть. Лучший результат на сегодняшний день — 96.43% (Graham, 2015).

Прим. переводчика: в репозитории http://rodrigob.github.io/are_we_there_yet собрана таблица лидеров по разным датасетам, в том числе по CIFAR-10.

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

Мои благодарности Ignacio Tonoli de Maussion, Per Harald Borgen, Jean-Luc Wingert, Sai Soundararaj, и Charlie Harrington за вычитку черновиков. И благодарность сообществу TFlearn за документацию и исходники.

Об авторе (Эмиль Воллнер)

Это первая статья из серии статей о глубоком обучении. Я потратил десять лет на изучение человеческого обучения. Работаю в бизнес-школе Оксфорда, инвестировал в образовательные стартапы и построил бизнес в сфере технологического обучения. В прошлом году я поступил в Ecole 42, чтобы найти применение своим знаниям в сфере машинного обучения.

Вы можете следить за моим прогрессом в Твиттере. Если у вас есть вопросы или пожелания, оставьте комментарий в Медиум.

Первоначально публиковалось в блоге FloydHub.

Transfer learning и тонкая настройка глубоких сверточных нейронных сетей / Блог компании Microsoft / Хабр

В предыдущей статье из цикла «Deep Learning» вы узнали о сравнении фреймворков для символьного глубокого обучения. В этом материале речь пойдет о глубокой настройке сверточных нейронных сетей для повышения средней точности и эффективности классификации медицинских изображений.

Цикл статей «Deep Learning»

1. Сравнение фреймворков для символьного глубокого обучения.
2. Transfer learning и тонкая настройка глубоких сверточных нейронных сетей.
3. Cочетание глубокой сверточной нейронной сети с рекуррентной нейронной сетью.

Примечание: далее повествование будет вестись от имени автора.

Введение

Распространенной причиной потери зрения является диабетическая ретинопатия (ДР) — заболевание глаз при диабете. Исследование пациентов с помощью флюоресцентной ангиографии потенциально способно снизить риск слепоты. Существующие тенденции исследований показывают, что глубокие сверточные нейросети (ГСНС) весьма эффективны для автоматического анализа больших наборов изображений и для выявления отличительных признаков, по которым можно распределить изображения на разные категории практически без ошибок. Обучение ГСНС редко происходит с нуля из-за отсутствия заранее заданных наборов с достаточным количеством изображений, относящихся к определенной области. Поскольку для обучения современных ГСНС требуется 2–3 недели, центр Berkley Vision and Learning Center (BVLC) выпустил итоговые контрольные точки для ГСНС. В этой публикации мы используем заранее обученную сеть: GoogLeNet. Сеть GoogLeNet обучена на большом наборе естественных изображений ImageNet. Мы передаем распознанные весов ImageNet в качестве начальных для сети, затем настраиваем заранее обученную универсальную сеть для распознавания изображений флюоресцентной ангиографии глаз и повышения точности предсказания ДР.

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

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

  • Методики предварительной обработки изображений для удаления шума и повышения контрастности.
  • Методика выделения отличительных признаков.
  • Классификация.
  • Предсказание.

Оливер Фауст и другие его коллеги предоставляют очень подробный анализ моделей, использующих явное выделение отличительных признаков ДР. Вуйосевич с коллегами создали двоичный классификатор на основе набора данных 55 пациентов, явным образом выделив отдельные отличительные признаки поражений. Некоторые авторы использовали методики морфологической обработки изображений для извлечения отличительных признаков кровеносных сосудов и кровотечений, а затем обучили машину опорных векторов на наборе данных из 331 изображения. Другие специалисты сообщают о точности 90% и чувствительности 90% в задаче двоичной классификации на наборе данных из 140 изображений.

Тем не менее все эти процессы связаны со значительными затратами времени и усилий. Для дальнейшего повышения точности предсказаний требуются огромные объемы маркированных данных. Обработка изображений и выделение отличительных признаков в наборах данных изображений — весьма сложный и длительный процесс. Поэтому мы решили автоматизировать обработку изображений и этап выделения отличительных признаков, используя ГСНС.

Глубокая сверточная нейросеть (ГСНС)

Для выделения отличительных признаков в изображениях требуются экспертные знания. Функции выделения в ГСНС автоматически формируют изображения для определенных областей, не используя никакие функции обработки отличительных признаков. Благодаря этому процессу ГСНС пригодны для анализа изображений:

  • ГСНС обучают сети с множеством слоев.
  • Несколько слоев работают вместе для формирования улучшенного пространства отличительных признаков.
  • Начальные слои изучают первостепенные признаки (цвет, края и пр.).
  • Дальнейшие слои изучают признаки более высокого порядка (в соответствии с входным набором данных).
  • Наконец, признаки итогового слоя подаются в слои классификации.

Слои C — свертки, слои S — пулы и выборки

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

Опрос. Pooling layer берет небольшие прямоугольные блоки из сверточного слоя и проводит подвыборку, чтобы сделать из этого блока один выход.

В этой публикации мы используем ГСНС GoogLeNet, разработанную в Google. Нейросеть GoogLeNet выиграла конкурс ImageNet в 2014 году, поставив рекорд по наилучшим единовременным результатам. Причины выбора этой модели — глубина работы и экономное использование ресурсов архитектуры.

Transfer learning и тонкая настройка глубоких сверточных нейросетей

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

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

  1. Новый набор данных меньше по размеру и аналогичен по содержанию исходному набору данных. Если объем данных невелик, то нет смысла проводить тонкую настройку ГСНС из-за чрезмерной подгонки. Поскольку данные схожи с изначальными, можно предполагать, что отличительные черты в ГСНС будут релевантны и для этого набора данных. Поэтому оптимальным решением является обучение линейного классификатора отличительным признаком СНС.
  2. Новый набор данных относительно крупный и аналогичен по содержанию исходному набору данных. Поскольку у нас больше данных, можно не беспокоиться о чрезмерной подгонке, если мы попытаемся провести тонкую настройку всей сети.
  3. Новый набор данных меньше по размеру и существенно отличается по содержанию от исходного набора данных. Поскольку объем данных невелик, будет вполне достаточно только линейного классификатора. Так как данные существенно отличаются, лучше обучать классификатор не с вершины сети, где содержатся более конкретные данные. Вместо этого лучше обучить классификатор, активировав его на более ранних слоях сети.
  4. Новый набор данных относительно крупный и существенно отличается по содержанию от исходного набора данных. Поскольку набор данных очень крупный, можно позволить себе обучить всю ГСНС с нуля. Тем не менее на практике зачастую все равно оказывается выгоднее использовать для инициализации весов из заранее обученной модели. В этом случае мы будем располагать достаточным объемом данных для тонкой настройки всей сети.

Тонкая настройка ГСНС. Решая вопрос предсказания ДР, мы действуем по сценарию IV. Мы проводим тонкую настройку весов заранее обученной ГСНС, продолжая обратное распространение. Можно либо провести тонкую настройку всех слоев ГСНС, либо оставить некоторые из ранних слоев неизменными (во избежание чрезмерной подгонки) и настроить только высокоуровневую часть сети. Это обусловлено тем, что на ранних слоях ГСНС содержатся более универсальные функции (например, определение краев или цветов), полезные для множества задач, а более поздние слои ГСНС уже ориентированы на классы набора данных ДР.

Ограничения transfer learning. Поскольку мы используем заранее обученную сеть, наш выбор архитектуры модели несколько ограничен. Например, мы не можем произвольным образом убрать сверточные слои из заранее обученной модели. Тем не менее благодаря совместному использованию параметров можно с легкостью запустить заранее обученную сеть для изображений разного пространственного размера. Это наиболее очевидно в случае сверточных и выборочных слоев, поскольку их функция перенаправления не зависит от пространственного размера входных данных. В случае с полносвязанными слоями этот принцип сохраняется, поскольку полносвязанные слои можно преобразовать в сверточный слой.

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

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

Существует множество способов дополнения данных, например, зеркальное отображение по горизонтали, случайная обрезка, изменение цветов. Поскольку цветовая информация этих изображений очень важна, мы применяем лишь поворот изображений на разные углы: на 0, 90, 180 и 270 градусов.

Замена входного слоя заранее обученной сети GoogLeNet на изображения ДР. Мы проводим тонкую настройку всех слоев, кроме двух верхних заранее обученных слоев, содержащих универсальные веса.

Тонкая настройка GoogLeNet. Используемая нами сеть GoogLeNet изначально была обучена на наборе данных ImageNet. Набор данных ImageNet содержит около 1 млн естественных изображений и 1000 меток/категорий. В нашем размеченном наборе данных ДР содержится около 30 000 изображений, относящихся к рассматриваемой области, и четыре метки/категории. Следовательно, этого набора данных ДР недостаточно для обучения сложной сети, какой является GoogLeNet: мы будем использовать веса из сети GoogLeNet, обученной по ImageNet. Мы проводим тонкую настройку всех слоев, кроме двух верхних заранее обученных слоев, содержащих универсальные веса. Первоначальный слой классификации loss3/classifier выводит предсказания для 1000 классов. Мы заменяем его новым двоичным слоем.

Заключение

Благодаря тонкой настройке можно применять усовершенствованные модели ГСНС в новых областях, где их было бы невозможно использовать иначе из-за недостатка данных или ограничений по времени и стоимости. Такой подход позволяет добиться существенного повышения средней точности и эффективности классификации медицинских изображений.

Если вы увидели неточность перевода, сообщите пожалуйста об этом в личные сообщения.

Нейронные сети с нуля. Обзор курсов и статей на русском языке, бесплатно и без регистрации

На Хабре периодически появляются обзоры курсов по машинному обучению. Но такие статьи чаще добавляют в закладки, чем проходят сами курсы. Причины для этого разные: курсы на английском языке, требуют уверенного знания матана или специфичных фреймворков (либо наоборот не описаны начальные знания, необходимые для прохождения курса), находятся на других сайтах и требуют регистрации, имеют расписание, домашнюю работу и тяжело сочетаются с трудовыми буднями. Всё это мешает уже сейчас с нуля начать погружаться в мир машинного обучения со своей собственной скоростью, ровно до того уровня, который интересен и пропускать при этом неинтересные разделы.

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

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

Для крупных разделов и видео-курсов указаны приблизительные временные затраты, необходимые знания, ожидаемые результаты и задания для самопроверки.

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

Вводные статьи

Требуемый уровень: школьное образование, знание русского языка.
Требуемое время: несколько часов.

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

Нейронки за 5 минут (слишком упрощённое описание, для гуманитариев, зато потребуется всего 5 минут)
Искусственные нейронные сети простыми словами (лучше потратить 15 минут на эту статью)
Основы ИНС (одна из четырёх статей из Учебник — Нейронные сети)
Нейронные сети для начинающих. Часть 1 и Часть 2
Нейронные сети, фундаментальные принципы работы, многообразие и топология
Искусственные нейронные сети и миниколонки реальной коры (девятая часть из курса Логика сознания)

ЗаданиеПрежде чем переходить к следующему уровню, создайте в онлайн конструкторе сеть. Посмотрите все 4 примера, и в последнем (спираль) обучите сеть за не более чем 100 эпох до уровня ошибки не более 0.1%, используя при этом минимальное количество нейронов и слоёв.

Расширяем горизонты

Требуемый уровень: базовое понимание работы нейронных сетей.
Требуемое время: несколько часов.

Краткий курс машинного обучения или как создать нейронную сеть для решения скоринг задачи
Самое главное о нейронных сетях. Лекция в Яндексе (рекомендую посмотреть только видео на 1 час, читать статью показалось тяжеловато)
Введение в архитектуры нейронных сетей
Что такое свёрточная нейронная сеть
Свёрточная нейронная сеть, часть 1: структура, топология, функции активации и обучающее множество
Зоопарк архитектур нейронных сетей. Часть 1 и Часть 2 (Особо вчитываться не надо, достаточно посмотреть красивые картинки и прочитать описание по диагонали)

ЗаданиеПеречислите основные:

  • типы задач, которые решают нейронные сети
  • типы архитектур нейронных сетей
  • функции активации
  • типы нейронов / слоёв

Углубляем знания

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

Курс о Deep Learning на пальцах от АФТИ НГУ (14 видеороликов, 15 часов, будет познавательно)
Материалы открытого курса OpenDataScience и Mail.Ru Group по машинному обучению (10 видеороликов, 20 часов, будет сложно)
Лекции Техносферы. Нейронные сети в машинном обучении (14 видеороликов, 25 часов, будет скучно)

Чтобы определиться самому и помочь с выбором остальным хабровчанам, я построил график падения интереса к курсу на основе падения количества просмотров каждого следующего ролика. Выводы неутешительные — мало кто доходит до конца. Самый большой процент дошедших до конца — у курса от АФТИ НГУ.


(График падения количества просмотров составлялся пару месяцев назад и текущая картина может немного отличаться).

Примеры применения на практике

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

ТОП30 самых впечатляющих проектов по машинному обучению за прошедший год (v.2018)
Улучшение качества изображения с помощью нейронной сети
Детектирование частей тела с помощью глубоких нейронных сетей
Классификация объектов в режиме реального времени
Раскрашиваем чёрно-белую фотографию с помощью нейросети
Смена пола и расы на селфи с помощью нейросетей
Как различать британскую и американскую литературу с помощью машинного обучения
Разделение текста на предложения с помощью Томита-парсера
WaveNet: новая модель для генерации человеческой речи и музыки
Анализ Корана при помощи AI
Сколько нужно нейронов, чтобы узнать, разведён ли мост Александра Невского?
Сколько котов на хабре?
Торговля знает, когда вы ждете ребенка
Стэнфордская нейросеть определяет тональность текста с точностью 85%
Топливо для ИИ: подборка открытых датасетов для машинного обучения

Другие материалы

Статьи и курсы, которые не вошли в мой обзор, но возможно вам понравятся.

Нейронные сети в картинках: от одного нейрона до глубоких архитектур (python, numpy)
Базовые принципы машинного обучения на примере линейной регрессии (python, numpy, матан)
Сверточная нейронная сеть, часть 2: обучение алгоритмом обратного распространения ошибки (матан)
Нейронные сети на stepik.org (в обзоре двухлетней давности его уже тогда называли устаревшим)
Курс по машинному обучению на Coursera от Яндекса и ВШЭ (курс доступен только после регистрации, NumPy, Pandas, Scikit-Learn)
Deep Learning For Coders (7 видеороликов, 15 часов, английский язык)
Курс Deep Learning от Google на udacity (английский язык)
Курс Структурирование проектов по машинному обучению на Coursera (платный, английский язык)

Другие статьи-обзоры на хабре по изучению машинного обучения

Где и как изучать машинное обучение? (английский язык)
Что читать о нейросетях 10 книг (английский язык)
Обучаемся самостоятельно: подборка видеокурсов по Computer Science (английский язык)
Обзор курсов по Deep Learning (английский язык)
10 курсов по машинному обучению на лето (английский/русский язык, платно/бесплатно)

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

Надеюсь, что у моей статьи будет меньше комментариев вида:

«Закинул в закладки. Смотреть я их, конечно, не буду.»

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

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

Машинное обучение глубокой нейронной сети с подкреплением на tensorflow.js: Трюки / Хабр

Обучать глубокие нейронные сети с нуля — задача не из простых.

Требуется много данных и времени на обучение, но ускорить процесс могут помочь некоторые трюки, о которых я и расскажу под катом.

Демонстрация прохождения простого лабиринта с использованием трюков. Длительность обучения сети: 1 час 06 минут. Запись ускорена в 8 раз.

Под каждую задачу нужно разрабатывать собственный набор трюков для ускорения обучения сети. Я поделюсь несколькими приёмами, которые помогли мне обучить сеть намного быстрее.

За теоретическими знаниями рекомендую перейти на канал sim0nsays.

А я расскажу о своих скромных успехах в обучении нейронных сетей.

Постановка задачи

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

У меня был выбор стратегии как обучать нейронную сеть.

Поощрять за успешное завершение поставленной задачи или поощрять по мере приближения к завершению поставленной задачи.

Я выбрал второй способ, по двум причинам:

  • Вероятность, что сеть когда либо самостоятельно доберётся до финиша очень мала, поэтому она будет обречена получать много отрицательного подкрепления. Это обнулит веса всех нейронов и сеть будет не способна к дальнейшему обучению.
  • Глубокие нейронные сети мощны. Не исключаю, что первый способ завершился бы успехом, если бы у меня были огромные вычислительные мощности и много времени на обучение. Я же пошёл по пути наименьших затрат — разработав трюки.

Архитектура нейронной сети

Архитектура разрабатывается экспериментально, основывается на опыте архитектора и удачи.

Архитектура для решения задачи:

  • 3 входных нейрона — координаты агента и значение пройденной ячейки (нормализуем в диапазоне от 0 до 1).
  • 2 скрытых слоя по 256 и 128 нейронов (уменьшаем размерность слоёв в сторону выхода сети).
  • 1 слой сброса случайных нейронов для устойчивости обучения сети.
  • 4 выходных нейрона — вероятности принятия решения выбора стороны для следующего шага.
  • Функция активации нейронов: sigmoid. Оптимизатор: adam.

sigmoid даёт на выходе 4 вероятности в диапазоне от 0 до 1, выбирая максимальный, получаем сторону для следующего шага: [jumpTop, jumpRight, jumpBottom, jumpLeft].

Разработка архитектуры

Переобучение возникает при использовании избыточно сложных моделей.

Это когда сеть запомнила тренировочные данные и для новых данных, которые сеть еще не видела, она будет работать плохо, потому что у сети не было необходимости искать обобщения, так как у нее в достатке было памяти для запоминания.

Недообучение — при недостаточно сложных моделей. Это когда у сети было мало тренировочных данных, чтобы найти обобщения.

Вывод: чем больше слоёв и нейронов в них, тем больше нужно данных для обучения.

Игровое поле

Правила игры

0 — Вступив на эту ячейка, агент уничтожается.
1..44 — Ячейки, значения которых увеличиваются с каждый шагом.
Чем дальше агент прошёл, тем большее вознаграждение он получит.
45 — Финиш. Обучения при этом не происходит, оно только когда все агенты уничтожены, а финиш — это исключение, которое просто использует уже обученную сеть для следующего прогнозирования с самого начала лабиринта.

Описание параметров

Агент имеет “усики” в четырёх направлениях от него — они играют роль разведки окружающей среды и являются описанием для координат агента и значения ячейки, на которой он стоит.

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

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

Трюки

Первые попытки обучения без трюков, занимали по несколько часов обучения и результат был далёк от завершения. Применив определённые приёмы, результата удалось достичь всего за один час и шесть минут!

Зацикливание агентов

В ходе обучения, сеть начинала принимать решения, делать ходы туда-сюда — проблема “использования”. Оба хода дают сети положительное вознаграждение, что останавливало процесс исследования лабиринта и не давало выбраться из локального минимума.

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

Исследовать или использовать

Чтобы исследовать пути вокруг текущего положения агента, был использован простой трюк: на каждом шагу, 5 агентов будут “добровольными” исследователями. Ход этих агентов будет выбран случайно, а не прогнозом нейронной сети.

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

Генетический алгоритм

Каждую эпоху на игровом поле участвуют 500 агентов. Прогнозирование для всех агентов выполняются в асинхронном режиме для всех агентов сразу, к тому же вычисления делегируются на gpu. Таким образом мы получаем более эффективное использование вычислительных мощностей компьютера, что приводит к сокращению времени на прогнозирование нейронной сети для 500 агентов одновременно.

Прогнозирование работает быстрее, чем обучение, следовательно сеть имеет больше шансов продвинуться дальше по лабиринту при наименьшем затрате времени и наилучшем результате.

Обучение на лучших в поколении

На протяжении эпохи, для 500 агентов сохраняются результаты их продвижения по лабиринту. Когда уничтожен последний агент, выбираются 5 лучших агентов из 500 — кто дошёл по лабиринту дальше всех.

На результатах лучших в эпохе, будет обучаться нейронная сеть.

Таким образом мы сократим объем использованной памяти не сохраняя и не обучая сеть на агентах, которые сеть не продвигают вперёд.

Завершение

Не являясь специалистом в данной области у меня получилось достичь некоторых успехов в обучении нейронной сети, получится и у Вас — дерзайте!

Стремитесь учиться быстрее компьютеров, пока у нас это получается лучше.

Материалы

Репозиторий с кодом
Запустить обучение в браузере
Документация по tensorflow.js, где также можно найти дополнительные ресурсы для изучения.

Книги

  • Глубокое обучение. Погружение в мир нейронных сетей

    С. Николенко, А. Кадурин, Е. Архангельская
  • Машинное обучение и TensorFlow

    Н. Шакла
  • Самообучающиеся системы

    С. И. Николенко, А. Л. Тулупьев
  • Обучение с подкреплением

    Р. С. Саттон, Э. Г. Барто
  • Самоорганизующиеся карты

    Т. Кохонен

Спасибо за внимание!

UPD: Reinforcement Learning Snake

Cочетание глубокой сверточной нейронной сети с рекуррентной нейронной сетью / Блог компании Microsoft / Хабр

Представляем вам завершающую статью из цикла по Deep Learning, в которой отражены итоги работы по обучению ГСНС для изображений из определенных областей на примере распознавания и тегирования элементов одежды. Предыдущие части вы найдете под катом.

Цикл статей «Deep Learning»

1. Сравнение фреймворков для символьного глубокого обучения.
2. Transfer learning и тонкая настройка глубоких сверточных нейронных сетей.
3. Cочетание глубокой сверточной нейронной сети с рекуррентной нейронной сетью.

Примечание: далее повествование будет вестись от имени автора.

Введение

Если говорить о роли одежды в обществе, распознавание вещей может иметь множество областей применения. Например, работа Лю и других авторов, посвященная определению и поиску немаркированных предметов одежды на изображениях, поможет распознавать наиболее схожие элементы в базе данных электронной коммерции. Янг и Ю смотрят на процесс распознавания элементов одежды с другой стороны: они считают, что эту информацию можно использовать в контексте видеонаблюдения, для выявления подозреваемых в преступлениях.

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

На эту работу меня вдохновили недавние усовершенствования в области машинного перевода, задача которых состоит в переводе отдельных слов или предложений. Теперь можно переводить намного быстрее с помощью рекуррентных нейросетей (РНС), добиваясь при этом высокой скорости. Кодер РНС читает исходный тег или метку и преобразует ее в векторное представление фиксированной длины, которое, в свою очередь, используется в качестве начального скрытого состояния декодера РНС, формирующего тег или метку. Мы предлагаем пойти по этому же пути, используя глубокую сверточную нейросеть (ГСНС) вместо кодера РНС. В течение последних лет стало ясно, что сети ГСНС могут создавать достаточное представление входного изображения, встраивая его в вектор фиксированной длины, который можно использовать для различных задач. Можно естественным образом использовать ГСНС в качестве кодировщика изображения: для этого сначала нужно провести предварительное обучение задаче классификации изображений, используя скрытый уровень в качестве входа для декодера РНС, формирующего теги.

Модель РНС-СНС для создания тегов изображений одежды

В этой работе будет использована заранее обученная по ImageNet модель GoogLeNet для извлечения компонентов СНС из набора данных ДР. Затем функции СНС для обучения модели РНС с длительной краткосрочной памятью для предсказания тегов ДР.

Архитектура GoogLeNet

Данные

Используем набор данных ДР: полный пайплайн для распознавания и классификации одежды людей в естественных условиях. Это решение может применяться в различных областях, например, в электронной коммерции, при проведении мероприятий, в интернет-рекламе и так далее. Пайплайн состоит из нескольких этапов: распознавания частей тела, различных каналов и визуальных атрибутов. ДР определяет 15 классов одежды и вводит эталонный набор оценочных данных для её классификации, состоящий более чем из 80 000 изображений. Также, мы используем набор данных ДР, чтобы предсказывать теги одежды для изображений, которые ранее не были проанализированы.

Изображения из тренировочных и тестовых наборов данных обладают совершенно разными показателями: разрешением, соотношением сторон, цветами и так далее. Для нейронных сетей нужны входные данные фиксированного размера, поэтому все изображения мы перевели в формат: 3 × 224 × 224.

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

Существует множество способов дополнения данных, например, зеркальное отображение по горизонтали, случайная обрезка, изменение цветов. Поскольку цветовая информация этих изображений очень важна, мы применяем лишь поворот изображений на разные углы: на 0, 90, 180 и 270 градусов.


Дополненные изображения ДР

Тонкая настройка GoogleNet для ДР

Чтобы справиться с проблемой предсказания тегов ДР, мы идем по сценарию тонкой настройки из предыдущей части. Используемая нами модель GoogLeNet изначально была обучена на наборе данных ImageNet. Набор данных ImageNet содержит около 1 млн естественных изображений и 1000 меток/категорий. В нашем размеченном наборе данных ДР содержится около 80 000 изображений, относящихся к категории «одежда», и 15 меток/категорий. Набора данных ДР недостаточно для обучения столь сложной сети, как GoogLeNet. Поэтому мы используем весовые данные из модели GoogLeNet, обученной по набору данных ImageNet. Проводим тонкую настройку всех уровней заранее обученной модели GoogLeNet путем непрерывного обратного распространения.
Замена входного слоя заранее обученной сети GoogLeNet на изображения ДР

Обучение РНС с длительной краткосрочной памятью

В этой работе мы используем модель РНС с длительной краткосрочной памятью, обладающей высокой производительностью при выполнении последовательных задач. В основе этой модели — ячейка памяти, кодирующая знания о наблюдаемых входных данных в каждый момент времени. Поведение ячейки управляется затворами, в роли которых используются слои, применяемые мультипликативно. Здесь используется три затвора:

  • забыть текущее значение ячейки (забыть затвор f),
  • прочитать входное значение ячейки (ввести затвор i),
  • вывести новое значение ячейки (вывести затвор o).

Рекуррентная нейросеть с длительной краткосрочной памятью

Блок памяти содержит ячейку «с», управляемую с помощью трех затворов. Синим показаны рекуррентные подключения: вывод «m» в момент времени (t–1) подается обратно в память во время «t» через три затвора; значение ячейки подается обратно через затвор «забыть»; предсказанное слово в момент времени (t–1) подается обратно в дополнение к выходу памяти «m» в момент времени «t» в Softmax для предсказания тега.

Модель с длительной краткосрочной памятью обучается для предсказания основных тегов для каждого изображения. В качестве входа используются функции ГСНС ДР (полученные с помощью GoogLeNet). Затем выполняется обучение модели с длительной краткосрочной памятью (LSTM) на основе сочетаний этих функций ГСНС и меток для заранее обработанных изображений.

Копия памяти LSTM создается для каждого изображения LSTM и для каждой метки таким образом, что все LSTM используют одинаковые параметры. Вывод (m)×(t−1) LSTM в момент времени (t –1) подается в LSTM в момент времени (t). Все рекуррентные подключения преобразуются в упреждающие подключения в окончательной версии. Мы видели, что подача изображения в каждый этап времени в качестве добавочного ввода дает неудовлетворительные результаты, поскольку сеть воспринимает помехи на изображениях и производит чрезмерную подгонку. Потери снижаются по отношению ко всем параметрам LSTM, верхнему уровню сверточной нейросети встраивания изображений и встраиванию меток.

Архитектура ГСНС-РНС для предсказания тегов ДР

Результаты

Мы применяем описанную выше модель для предсказания тегов ДР. Точность предсказаний тегов в этой модели быстро повышается в первой части итераций и стабилизируется приблизительно после 20 000 итераций.

Каждое изображение в наборе данных ДР состоит только из уникальных типов одежды, нет изображений, на которых сочетаются разные типы одежды. Несмотря на это, при тестировании изображений с несколькими типами одежды наша обученная модель достаточно точно создает теги для этих не обработанных ранее тестовых изображений (точность составила около 80%).

Ниже показан пример выходных данных нашего предсказания: на тестовом изображении вы видите человека в костюме и человека в футболке.

Тестовое изображение, не анализированное ранее

На приведенном ниже рисунке показано предсказание тегов GoogLeNet с помощью модели GoogLeNet с обучением по ImageNet.

Предсказание тегов GoogLeNet для тестового изображения с помощью модели GoogLeNet с обучением по ImageNet

Как видно, предсказание по этой модели не очень точное, поскольку тестовое изображение получает тег «виндзорский галстук». На приведенном ниже рисунке показано предсказание тегов ДР с помощью описанной выше модели РНС-ГНСС с длительной краткосрочной памятью. Как видно, предсказание по этой модели весьма точное, поскольку наше тестовое изображение получает теги «сорочка, футболка, верхняя часть туловища, костюм».

Предсказание тегов GoogLeNet для тестового изображения с помощью модели РНС-ГНСС с длительной краткосрочной памятью

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

Заключение

В этой работе мы сравниваем точность предсказания тегов модели GoogLeNet и модели РНС-ГНСС с длительной краткосрочной памятью. Точность предсказания тегов второй модели значительно выше. Для её обучения использовали относительно небольшое количество обучающих итераций, порядка 10 000. Точность предсказаний второй модели быстро повышается с увеличением количества обучающих итераций и стабилизируется приблизительно после 20 000 итераций. Для этой работы мы использовали только один ГП.

Благодаря тонкой настройке можно применять усовершенствованные модели ГСНС в новых областях. Кроме того, объединенная модель ГСНС-РНС помогает расширять обученную модель для решения совершенно других задач, таких как формирование тегов для изображений одежды.

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

Если вы увидели неточность перевода, сообщите пожалуйста об этом в личные сообщения.

обзор Deep Learning в Computer Vision (часть 2) / Блог компании Московский физико-технический институт (МФТИ) / Хабр

Продолжаем постигать современную магию (компьютерное зрение). Часть 2 не значит, что нужно сначала читать часть 1. Часть 2 значит, что теперь всё серьёзно — мы хотим понять всю мощь нейросетей в зрении. Детектирование, трекинг, сегментация, оценка позы, распознавание действий… Самые модные и крутые архитектуры, сотни слоёв и десятки гениальных идей уже ждут вас под катом!

В прошлой серии

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

Ещё в предыдущей статье поговорили про разные типы архитектур (да, те самые таблички, которые я делал месяц,), и тут Google времени зря не терял: они выпустили ещё одну крайне быструю и точную архитектуру EfficientNet. Они создали её, используя NAS и специальную процедуру Compound Scaling. Ознакомьтесь со статьёй, оно того стоит.

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

Вот люди говорят: “распознавание изображений”. Но что такое “распознавание”? Что такое “понимание (сцены)”? На мой взгляд, ответы на эти вопросы зависят от того, что именно мы хотим “распознать”, и что именно хотим “понять”. Если мы строим Искусственный Интеллект, который будет извлекать информацию о мире из визуального потока также эффективно (или даже лучше), как люди, то нужно идти от задач, от потребностей. Исторически сложилось, что современное “распознавание” и “понимание сцены” можно разделить на несколько конкретных задач: классификация, детектирование, трекинг, оценка позы и точек лица, сегментация, распознавание действий на видео и описание картинки текстом. В этой статье речь пойдёт о первых двух задачах из списка (уп-с, спойлер третьей части), поэтому текущий план такой:

  1. Найди меня, если сможешь: детектирование объектов
  2. Детектирование лиц: не пойман — не вор
  3. Много букв: детектирование (и распознавание) текста
  4. Видео и трекинг: единым потоком

Let’s rock, superstars!

Найди меня, если сможешь: детектирование объектов

Итак, задача звучит просто — дана картинка, необходимо найти на ней объекты заранее заданных классов (человек, книга, яблоко, артезиано-нормандский бассет-гриффон и т.д.). Для того, чтобы решить эту задачу с помощью нейросетей, поставим её в терминах тензоров и машинного обучения.

Мы помним, что цветная картинка — это тензор (H,W,3) (если не помним, то есть часть 1). Раньше мы умели только классифицировать картинку целиком, теперь же наша цель — предсказать положения интересующих объектов (координаты пикселей) на картинке и их классы.

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

Классификация? Регрессия?
Напомню, что мы говорим про задачи машинного обучения. В задаче классификации в качество истинных меток для объектов выступают метки классов, и мы предсказываем класс объекта. В задаче регрессии в качестве истинных ответов выступают вещественные числа, и мы предсказываем число (например: вес, рост, зарплату, количество персонажей, которые умрут в очередной серии Игры Престолов…). Более подробно — милости прошу в 3-ю лекцию DLSchool (ФПМИ МФТИ).

Но координаты объекта, вообще говоря, можно по-разному формализовать, в DL есть три основных способа: детектирование (боксы объектов), оценка позы (ключевые точки объектов) и сегментация («маски» объектов). Сейчас поговорим про предсказание именно bounding box’ов, точки и сегментация будут дальше по тексту.
В основном датасеты для детектирования размечены box’ами в формате: “координаты левого верхнего и правого нижнего углов для каждого объекта на каждой картинке” (этот формат ещё называют top-left, bottom-right), и большинство нейросетевых подходов предсказывают именно эти координаты.
Про датасеты и метрики в задаче детектирования
После постановки задачи лучше всего посмотреть, какие есть данные для обучения и какие используются метрики для измерения качества. Об этом я не спеша рассказываю в первой половине 13-ой лекции от Deep Learning School (на х2.0 самое то).

Перед тем как окунуться в виды нейросетей для детекции, давайте вместе подумаем, как вообще можно решать задачу детектирования чего-либо на изображениях. Наверное, если мы хотим найти определённый объект на картинке, то мы примерно знаем, как он выглядит и какую должен занимать на изображении площадь (хотя она может и изменяться).
Изобретаем детектирование с нуля
Наивным и простейшим подходом будет просто сделать алгоритм “поиска шаблона”: пусть картинка 100х100 пикселей, и мы ищем футбольный мяч. Пусть есть шаблон мяча 20х20 пикселей. Возьмём этот шаблон и будем проходиться им прямо как свёрткой по всей картинке, считая попиксельную разность. Так работает template matching (ещё часто используется какой-либо тип корреляции вместо попиксельной разности).

Если шаблона нет, но есть нейросеть-классификатор, то можем поступить так: будем идти окном фиксированного размера по картинке и предсказывать класс текущей области картинки. Потом просто скажем, что самые вероятные регионы объектов — те, где классификатор ответил уверенно. Таким образом проблему того, что объект выглядит внешне по-разному, мы нейросетью решить можем (так как она обучалась на классификацию на весьма разнообразной выборке).

Но тут же всплывает проблема — объекты на картинках имеют разный размер. Тот же футбольный мяч может быть во всю высоту/ширину картинки, а может быть далеко у ворот, занимая всего 10-20 пикселей из 1000. Хочется написать Brute Force алгоритм: будем просто в цикле перебирать размеры окна. Допустим, у нас 100х200 пикселей, тогда будем идти окном 2х2, 2Х3, 3х2, 2х4, 4х2, 3х3…, 3х4, 4х3… Думаю, вам стало понятно, что количество возможных окон будет 100*200, и причём каждым мы проходимся по картинке, совершая (100-W_window) * (200 — H_window) операций классификации, что занимает немало времени. Боюсь, мы не дождёмся, пока такой алгоритм отработает.

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

Далее я иногда буду опираться на новый обзор области детектирования от января 2019 (картинки тоже будут из него). Это просто must read, если хотите быстро получить максимально широкий взгляд на DL в детекции.

Одной из первых статей, посвящённых детектированию и локализации с помощью CNN, была сеть Overfeat. Авторы утверждают, что впервые использовали нейросеть для детектирования на ImageNet, переформулировав задачу и изменив лосс. Подход, кстати, был практически end-to-end (ниже — схема Overfeat).

Следующей важной архитектурой стала изобретённая исследователями из FAIR в 2014 году нейросеть Region-based Convolutional Neural Network (RCNN). Суть её в том, что она предсказывает сначала много так называемых “регионов интереса” (RoI’s), внутри которых потенциально могут быть объекты (с помощью алгоритма Selective Search), и уже их классифицирует и уточняет координаты боксов с помощью CNN.
Правда подобный пайплайн делал всю систему медленной, ведь мы прогоняли через нейросеть каждый регион (тысячи раз делали forward pass). Уже через год тот же Ross Girshick из FAIR улучшил RCNN до Fast-RCNN. Здесь идея была в том, чтобы поменять местами Selective Search и предсказание сетью: сначала пропускаем через предобученную нейросеть всю картинку, а потом поверх выданного feature map’а сети-backbone’а предсказываем регионы интереса (например, с помощью того же Selective Search, но там есть и другие алгоритмы). Было всё ещё довольно медленно, куда медленнее, чем real-time (пока что будем считать, что real-time — это меньше 40 миллисекунд на одну картинку).
На скорость влияла больше всего уже не CNN, а сам алгоритм генерации боксов, поэтому решено было заменить его на вторую нейросеть — Region Proposal Network (RPN), которая будет обучаться предсказывать регионы интереса объектов. Так появилась Faster-RCNN (да, над названием явно долго не думали). Схема:
Потом было ещё улучшение в виде R-FCN, о нём подробно говорит не будем, но хочу упомянуть Mask-RCNN. Mask-RCNN — уникальную в своём роде, первая нейросеть, которая решает и задачу детектирования, и instance-сегментации одновременно — она предсказывает точные маски (силуэты) объектов внутри bounding box’ов. Её идея на самом деле довольно проста — есть две ветки: для детекции и для сегментации, и нужно обучать сеть на обе задачи сразу. Главное — иметь размеченные данные. Сам по себе Mask-RCNN устроен очень похоже на Faster-RCNN: backbone тот же, но в конце две «головы» (так часто называют последние слои нейросети) под две разные задачи.
Это были так называемые Two-Stage (или Region-based) подходы. Параллельно с ними в DL-детектировании развивались аналоги — One-Stage подходы. К ним можно отнести такие нейросети, как: Single-Shot Detector (SSD), You Only Look Once (YOLO), Deeply Supervised Object Detector (DSOD), Receptive Field Block Network (RFBNet) и многие другие (см. карту ниже, из этого репозитория).
One-stage подходы, в отличие от two-stage, не используют отдельный алгоритм для генерации боксов, а просто предсказывают несколько координат боксов для каждого feature map’а, выданного свёрточной нейросетью. Подобным образом действует YOLO, SSD слегка отличается, но идея одна: 1х1 свёртка предсказывает из полученных feature map’ов много чисел по глубине, однако мы заранее договариваемся, какое число что значит.

Например, предсказываем из feature map’a размера 13х13х256 feature map 13х13х(4*(5+80)) чисел, где по глубине мы для 4 боксов предсказываем по 85 чисел: первые 4 числа в последовательности всегда — координаты бокса, 5-ое число — уверенность в боксе, и 80 чисел — вероятности каждого из классов (классификация). Это нужно, чтобы потом подать нужные числа в нужные лоссы и правильно обучить нейросеть.
Хочу обратить внимание на то, что качество работы детектора напрямую зависит от качества работы нейросети для извлечения признаков (то есть backbone-нейросети). Обычно в этой роли выступает одна из архитектур, о которых я говорил в предыдущей статье (ResNet, SENet и др.), однако иногда авторы придумывают собственные более оптимальные архитектуры (например, Darknet-53 в YOLOv3) или модификации (например, Feature Pyramid Pooling (FPN)).

Снова отмечу, что мы обучаем сеть и на классификацию, и на регрессию одновременно. В сообществе это принято называть multi-task loss: в одном лоссе фигурирует сумма лоссов для нескольких задач (с некоторыми коэффициентами).

Новости с передовой про Multitask Loss
На Machines Can See 2019 один из докладчиков применял multi-task loss для 7-ми задач одновременно, Карл. Оказалось, что некоторые задачи были изначально поставлены в противовес друг другу и получился “конфликт”, что мешало сети учиться лучше, чем если обучать на каждую задачу по-отдельности. Вывод: если используете multi-task loss, убедитесь, что эти самые multi-task’и не конфликтуют по постановке (например, предсказание границ объектов и их внутренней сегментации может друг другу мешать, поскольку эти вещи могут опираться внутри сети на разные признаки). Автор же обошёл это с помощью добавления отдельных Squeeze-and-Excitation блоков для каждой задачи.

Недавно вышли статьи от 2019 года, в которых авторы заявляют о ещё лучшем соотношении скорость/точность в задаче детекции с помощью предсказания боксов на основе точек. Я говорю о статьях “Objects as Points” и “CornerNet-Lite”. ExtremeNet является модификацией CornerNet. Кажется, сейчас их можно назвать SOTA в детекции с помощью нейросетей (но это не точно).

UPD (25 апреля 2020): На данный момент среди детекторов значительно выделяется YOLOv4, в которой авторы указывают на наилучшее соотношение скорость-качество среди практически всех остальных нейросетевых детекторов.

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

Ниже я привёл таблицы нейросетей в детектировании со ссылками на код и кратким описанием фишек каждой сети. Я постарался собрать только те сети, которые действительно важно знать (по крайней мере, их идеи), чтобы иметь хорошее представление об object detection сегодня:

Нейросетевые детекторы (two-stage)

Нейросетевые детекторы (one-stage)

Нейросетевые детекторы (разное)

Нейросетевые детекторы (на основе точек)

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

Архитектуры — это прекрасно, но детектирование является прежде всего практической задачей. “Не имей сто сетей, а имей хотя бы 1 работающую” — таков мой message. В таблице выше есть ссылки на код, но лично я редко сталкиваюсь с запуском детекторов непосредственно из репозиториев (по крайней мере, с целью дальнейшего деплоя в продакшн). Чаще для этого используется какая-либо библиотека, например, TensorFlow Object Detection API (см. практическую часть моего занятия) или библиотека от исследователей из CUHK. Предлагаю вашему вниманию очередную супер-таблицу (они ведь вам нравятся, да?):

Библиотеки для запуска моделей детектирования

Часто детектировать нужно объект только одного класса, но специфичного и весьма вариативного. Например, детектировать все лица на фото (для дальнейшей верификации/подсчёта людей), детектировать людей целиком (для ре-идентификации/подсчёта/трекинга) или детектировать текст на сцене (для OCR/перевода слов на фото). В целом, подход “обычной” детекции здесь до определённой степени сработает, но в каждой из этих подзадач есть свои трюки, чтобы улучшить качество.

Детектирование лиц: не пойман — не вор

Здесь появляется некоторая специфика, поскольку лица часто занимают достаточно малую часть изображения. Плюс люди не всегда смотрят в камеру, часто лицо видно лишь сбоку. Одним из первых подходов к распознаванию лиц был знаменитый детектор Виолы-Джонса на основе каскадов Хаара, изобретённый ещё в 2001 году.
Нейросети тогда были не в моде не были ещё так сильны в зрении, однако старый добрый hand-crafted подход делал своё дело. В нём активно использовались несколько типов специальных масок-фильтров, которые помогали извлекать лицевые регионы с изображения и их признаки, и далее эти признаки подавались в AdaBoost-классификатор. Кстати, этот метод действительно нормально работает и сейчас, он достаточно быстрый и запускается “из коробки” с помощью OpenCV. Недостаток этого детектора в том, что он видит только лица, развёрнутые фронтально к камере. Стоит лишь немного повернуться, и стабильность детекции нарушается.

Для подобных более сложных случаев можно использовать dlib. Это C++-библиотека, в которой реализованиы многие алгоритмы зрения, в том числе для детектирования лиц.

Из нейросетевых подходов в детектировании лиц особенно значимым является Multi-task Cascaded CNN (MTCNN) (MatLab, TensorFlow). В целом, она и сейчас активно используется (в том же facenet).

Идея MTCNN — использовать для предсказания положения лица и его особых точек три нейросети последовательно (поэтому и “каскад”). Особых точек лица в данном случае ровно 5: левый глаз, правый глаз, левый край губ, правый край губ и нос. Первая нейросеть из каскада (P-Net) используется для генерации потенциальных регионов лица. Вторая (R-Net) — для улучшения координат полученных боксов. Третья (O-Net) нейросеть ещё раз регрессирует координаты боксов и, помимо того, предсказывает 5 ключевых точек лица. Multi-task эта сеть потому, что решаются три задачи: регрессия точек боксов, классификация лицо/не лицо для каждого бокса и регрессия точек лица. Причём MTCNN делает это всё в real-time, то есть ей требуется менее 40 ms на одну картинку.
Как, вы всё ещё не читаете статьи с ArXiv самостоятельно?
В таком случае рекомендую попробовать прочитать оригинальную статью про MTCNN, если уже имеете некоторый бекграунд в свёрточных сетях. Эта статья занимает всего 5 страниц, но в ней изложена вся нужная для понимания подхода информация. Попробуйте, вдруг затянет 🙂

Из современных State-of-the-Art можно отметить Dual Shot Face Detector (DSFD) и FaceBoxes. FaceBoxes имеет возможность быстрого запуска на CPU (!), а DSFD отличился лучшим качеством (вышел в апреле 2019 года). DSFD устроен посложнее, чем MTCNN, поскольку внутри сети используются специальный модуль для улучшения признаков (с dilated convolutions), две ветки их обработки и специальные типы лоссов. Кстати, с dilated convolutions мы ещё не раз столкнёмся в статьях про сегментацию в следующей части. Ниже пример работы DSFD (впечатляет, не правда ли?).
Чтобы научиться ещё и распознавать лица, не забудьте заглянуть в предыдущую статью серии, там я про это вкратце рассказал.

Много букв: детектирование (и распознавание) текста

Обратите внимание на фото выше. Легко заметить, что, если предсказывать bounding box’ы, параллельные осям координат (как мы делали раньше), то получится весьма некачественно. Часто это оказывается весьма критично, если мы хотим, например, подать потом эти боксы на вход recognition-нейросети, которая по картинке будет предсказывать текст.

В таких случаях принято предсказывать повёрнутые bounding box’ы, или и вовсе ограничивать текст многоугольниками вместо прямоугольников, если он изогнутый (примеры ниже). С предсказанием повёрнутых боксов справляется, например, EAST-детектор.

Идея EAST-детектора в том, чтобы предсказывать не координаты углов боксов, а следующие три вещи:

  1. Text Score Map’ы (вероятность нахождения текста в каждом пикселе)
  2. Угол поворота каждого бокса
  3. Расстояния до границ прямоугольника для каждого пикселя

Таким образом, это больше напоминает задачу сегментации (выделения масок текста), нежели детектирования. Поясняющая картинка из arxiv-статьи:

Задача распознавания текста (а значит и его детектирования) весьма популярна, поэтому есть и аналоги:TextBoxes++ (Caffe) и SegLinks, однако EAST, на мой взгляд, наиболее прост и доступен.

После детектирования текста хочется сразу скормить его другой нейросети, чтобы распознать его и выдать строку символов. Здесь можно заметить интересную смену модальности — из картинок в текст. Бояться этого совсем не стоит, ведь всё зависит лишь от того, какова архитектура сети, что именно предсказывается на последнем слое и какой используется лосс. Например, MORAN (код на PyTorch) и ASTER (код на TensorFlow) вполне справляются с поставленной задачей.

В них нет чего-то сверхъестественного, однако очень грамотно используются сразу два принципиально разных типа нейросетей: CNN и RNN. Первое нужно для извлечения признаков из картинки, а второе для генерации текста. Подробнее на примере MORAN’а: ниже архитектура его распознающей сети.

Однако несмотря на повёрнутые боксы от EAST’а, сетям-распознавателям на вход всё равно приходит прямоугольная картинка, а значит текст внутри неё может занимать далеко не всё пространство. Для того, чтобы распознавателю было проще предсказать по картинке непосредственно текст на ней, можно преобразовать её определённым способом.

Можем применить афинное преобразование ко входной картинке, чтобы растянуть/повернуть текст. Этого можно добиться с помощью Spatial Transformet Network (STN), поскольку она самостоятельно выучивает подобные преобразования и легко встраивается в другие нейронные сети (кстати, можно подобное выравнивание для любой картинки делать, не только для текста). Ниже пример до/после STN.

Подробно про STN здесь рассказывать нет смысла, поскольку есть замечательная статья на Хабре (картинка взята оттуда, спасибо автору) и код на PyTorch.

Но MORAN (та самая нейросеть для распознавания текста) поступает ещё умнее — она не ограничивается семейством афинных преобразований, а предсказывает для каждого пикселя входной картинки карту смещений по x и по y, таким образом добиваясь любого преобразования, которое улучшит обучение сети для распознавания. Этот метод называется rectification, то есть исправление картинки с помощью вспомогательной нейросети (rectifier’а). Ниже сравнение картинки после афинного преобразования и после ректификации:

Однако помимо подходов к распознаванию текста «модульно» (сеть детекции -> сеть распознавания), есть end-to-end архитектуры: на входе картинка, а на выходе — детекции и распознанный внутри них текст. И всё это единым пайплайном, который обучается на обе задачи сразу. В этом направлении есть внушительная работа Fast Oriented Text Spotting with a Unified Network (FOTS) (код на PyTorch), где авторы также отмечают, что end-to-end подход в два раза быстрее, чем «детекция+распознавание». Ниже схема нейросети FOTS, особую роль играет блок RoiRotate, благодаря которому есть возможность «прокидывать градиенты» с сети для распознавания на нейросеть для детекции (это и правда сложнее, чем кажется).
К слову, каждый год проходит конференция ICDAR, к которой приурочены несколько соревнований по распознаванию текста на самых различных изображениях.

Текущие проблемы в детектировании

На мой взгляд, главная проблема в детектировании сейчас не качество модели-детектора, а данные: их обычно долго и дорого размечать, особенно если классов, которые нужно детектировать, очень много (но кстати есть пример решения для 500 классов). Поэтому многие работы сейчас посвящены генерации как можно более правдоподобных данных «синтетически» и получения разметки “бесплатно”. Ниже картинка из моего диплома статьи от Nvidia, в которой речь идёт как раз о генерации синтетических данных.
Но всё же здорово, что теперь мы можем точно сказать, где на картинке что находиться. И если хотим, например, посчитать количество чего-то на кадре, то достаточно лишь задетектить это и выдать количество боксов. В детекции людей хорошо работает и обычная YOLO, просто главное подать много данных. Тот же Darkflow подойдёт, а класс «человек» встречается почти во всех крупных датасетах по детектированию. Так что если хотим посчитать с помощью камеры количество людей, которые прошли мимо, скажем, за одни сутки, или количество товаров, которые взял человек в магазине, просто задетектим и выдадим количество…
Стоп. Но ведь если мы будем детектировать людей на каждом изображении с камеры, то мы можем посчитать их количество на одном кадре, а на двух — уже нет, поскольку не сможем сказать, где какой именно человек. Нам необходим алгоритм, который позволит считать именно уникальных людей в видеопотоке. Им может быть алгоритм ре-идентификации, но когда речь заходит про видео и детекцию, грех не использовать алгоритмы трекинга.

Видео и трекинг: единым потоком

До сих пор мы говорили только про задачи на картинках, но самое-то интересное происходит на видео. Чтобы решать то же распознавание действий, нам необходимо использовать не только так называемую пространственную (spatial) компоненту, но и временнУю (temporal), поскольку видео — это последовательность изображений во времени.
Трекинг — это аналог детектирования изображений, но для видео. То есть мы хотим научить сеть предсказывать не бокс на картинке, а треклет во времени (который есть по сути последовательность боксов). Ниже пример изображения, на котором показаны «хвосты» — треки этих людей на видео.
Давайте подумаем, как можно решать задачу трекинга. Пусть есть видео, и его кадры #1 и #2. Рассмотрим пока что только один объект — трекаем один мячик. На кадре #1 мы можем использовать детектор, чтобы детектировать его. На втором тоже можем детектировать мячик, и если он там там один, то всё хорошо: говорим, что бокс на предыдущем кадре — это бокс того же мяча, что и на кадре #2. Так же можно продолжать и на остальные кадры, ниже gif из курса по зрению pyimagesearch.
Кстати, в целях экономии времени можем не запускать нейросеть на втором кадре, а просто “вырезать” бокс мяча из первого кадра и искать ровно такой же на втором кадре корреляцией или попиксельно. Такой подход утилизируют корреляционные трекеры, они считаются простыми и более-менее надёжными, если мы имеем дело с простыми случаями по типу “трекинг одного мяча перед камерой в пустой комнате”. Такую задачу ещё называют Visual Object Tracking. Ниже пример работы корреляционного трекера на примере одного человека.
Однако если детекций/людей несколько, то нужно уметь сопоставлять боксы с кадра #1 и с кадра #2. Первая идея, которая приходит в голову — попробовать сопоставлять бокс тому, который имеет с ним наибольшую область пересечения (IoU). Правда, в случае нескольких перекрывающихся детекций такой трекер будет нестабилен, поэтому нужно использовать ещё больше информации.
Подход с IoU опирается лишь на «геометрические» признаки детекций, то есть просто пытается сопоставить их по близости на кадрах. Но ведь у нас в распоряжении целое изображение (даже два в данном случае), и мы можем использовать то, что внутри этих детекций — «визуальные» признаки. Плюс к этому мы имеем историю детекций для каждого человека, что позволяет более точно предсказывать его следующее положение на основе скорости и направления движения, это условно можно назвать «физические» признаки.
Одним из первых real-time трекеров, который был вполне надёжен и умел справляться со сложными ситуациями, был опубликованный в 2016 году Simple Online and Realtime Traker (SORT) (код на Python). SORT не использовал какие-либо визуальные признаки и нейросети, а лишь оценивал ряд параметров каждого бокса на каждом кадре: текущую скорость (по x и по y отдельно) и размер (высота и ширина). Соотношение сторон (aspect ratio) бокса всегда берутся от самой первой детекции этого бокса. Далее скорости предсказываются с помощью фильтров Калмана (они вообще добро и свет в мире обработке сигналов), строится матрица пересечений боксов по IoU и детекции назначаются венгерским алгоритмом.

Если вам кажется, что математики уже стало многовато, то в этой статье всё доступно объясняется (это ж medium :).

Уже в 2017 году вышла модификация SORT’а в виде DeepSORT (код на TensorFlow). DeepSORT уже стал применять нейросеть для извлечения визуальных признаков, используя их для разрешения коллизий. Качество трекинга выросло — не зря он считается одним из лучших онлайн-трекеров сегодня.

Область трекинга и правда активно развивается: есть и трекеры с сиамскими нейросетями, и трекеры с RNN. Следует держать руку на пульсе, ведь в любой день может выйти (или уже вышла) ещё более точная и быстрая архитектура. Кстати, за подобными вещами очень удобно следить на PapersWithCode, там всегда ссылки на статьи и код к ним (если он есть).

Послесловие

Мы уже действительно многое пережили и многое узнали. Но компьютерное зрение — крайне обширная область, а я — крайне упрямый человек. Именно поэтому мы ещё увидимся в третьей статье этого цикла (будет ли она последней? Кто знает…), где более подробно обсудим сегментацию, оценку позы, распознавание действий на видео и генерацию описания по изображению с помощью нейросетей.

P.S. хочу выразить особую благодарность Вадиму Горбачёву за его ценные советы и комментарии при подготовке этой и предыдущей статьи.

Нейронные сети

против глубокого обучения

Разница между нейронными сетями и глубоким обучением

В связи с масштабным переходом на современные технологии, для трансформации бизнеса нужны не только большие данные и Hadoop. Сегодняшние фирмы движутся в сторону ИИ и используют машинное обучение в качестве своей новой техники. Нейронные сети или коннекционистские системы — это системы, вдохновленные нашей биологической нейронной сетью. Такие системы обучены обучаться и адаптироваться в соответствии с потребностями.Например, в случае распознавания изображений, как только они отождествляются с кошками, они могут легко использовать этот набор результатов для разделения изображений с кошками и изображений без кошек. При этом у них нет никаких предварительных знаний о характеристиках кошки, но они развивают свой собственный набор уникальных особенностей, которые помогают в их идентификации. Другой термин, который тесно связан с этим, — глубокое обучение, также известное как иерархическое обучение. Это основано на представлениях данных обучения, которые противоположны алгоритмам, основанным на задачах.Кроме того, его можно разделить на контролируемые, полу-контролируемые и неконтролируемые методы обучения. Существует несколько архитектур, связанных с глубоким обучением, таких как глубокие нейронные сети, сети убеждений и повторяющиеся сети, применение которых связано с обработкой естественного языка, компьютерным зрением, распознаванием речи, фильтрацией социальных сетей, распознаванием звука, биоинформатикой, машинным переводом, дизайном лекарств и списком. продолжается и продолжается. Давайте подробно обсудим нейронные сети и глубокое обучение в нашем посте.

Прямое сравнение нейронных сетей и глубокого обучения (Инфографика)

Ниже приведены 3 лучших сравнения нейронных сетей и глубокого обучения:

Ключевые различия между нейронными сетями и глубоким обучением

Различия между нейронными сетями и глубоким обучением объясняются в пунктах, представленных ниже:

  1. Нейронные сети используют нейроны, которые используются для передачи данных в виде входных и выходных значений.Они используются для передачи данных с помощью сетей или подключений. С другой стороны, глубокое обучение связано с преобразованием и извлечением функции, которая пытается установить связь между стимулами и соответствующими нейронными реакциями, присутствующими в мозге.
  2. Области применения нейронных сетей включают идентификацию системы, управление природными ресурсами, управление процессами, управление транспортными средствами, квантовую химию, принятие решений, игры, идентификацию лиц, распознавание образов, классификацию сигналов, распознавание последовательностей, распознавание объектов, финансы, медицинскую диагностику, визуализацию. , интеллектуальный анализ данных, машинный перевод, фильтрация спама в электронной почте, фильтрация социальных сетей и т. д.в то время как применение глубокого обучения включает автоматическое распознавание речи, распознавание изображений, обработку визуального искусства, обработку естественного языка, открытие лекарств и токсикологию, управление взаимоотношениями с клиентами, механизмы рекомендаций, мобильную рекламу, биоинформатику, восстановление изображений и т. д.
  3. Критика, встречающаяся в отношении нейронных сетей, включает проблемы обучения, теоретические проблемы, проблемы с оборудованием, практические контрпримеры критике, гибридные подходы, тогда как для глубокого обучения она связана с теорией, ошибками, киберугрозой и т. Д.

Нейронные сети и таблица сравнения глубокого обучения

Ниже приводится ключевое сравнение нейронной сети и глубокого обучения.

Основа для сравнения Нейронные сети Глубокое обучение
Определение Класс алгоритмов машинного обучения, в котором искусственный нейрон образует базовую вычислительную единицу, а сети используются для описания взаимосвязи друг с другом Это класс алгоритмов машинного обучения, который использует несколько уровней нелинейных модулей обработки для преобразования и извлечения признаков.Он также представляет концепции в нескольких иерархических формах, соответствующих различным уровням абстракции.
Компоненты Нейроны: Нейрон, помеченный как j, получает входные данные от предшествующих нейронов, часто в форме функции идентичности, чтобы обеспечить выход.
Связи и веса: Связь является жизненно важным компонентом между выходным нейроном i и входным нейроном j. Затем каждое соединение идентифицируется весом ij.
Функция распространения: Используется для обеспечения ввода для результирующего вывода.
Правило обучения: Используется для изменения параметров нейронной сети для получения благоприятного результата.
Материнская плата: Набор микросхем материнской платы — это компонент, связанный с глубоким обучением, которое, в частности, основано на линиях PCI-e.
Процессоры : Тип графического процессора, необходимый для глубокого обучения, должен зависеть от типа сокета, количества ядер и стоимости процессора.
ОЗУ, физическая память и хранилище: Алгоритмы глубокого обучения требуют большого использования ЦП, хранилища и области памяти, поэтому наличие богатого набора этих компонентов является обязательным.
PSU: С увеличением объема памяти, ЦП и хранилища также становится важным использовать большой блок питания, способный выдержать огромную мощность.
Архитектура Нейронные сети прямого распространения: Самый распространенный тип архитектуры содержит первый уровень в качестве входного, в то время как последний слой является выходным слоем, а все промежуточные уровни являются скрытыми.
Рекуррентные сети: Эта архитектура состоит из направленных циклов в графе соединений. Биологически реалистичная архитектура также может вернуть вас с того места, где вы начали. Их сложно тренировать, и они чрезвычайно динамичны.
Симметрично соединенные сети: Симметричная архитектура удержания соединений, которая более или менее похожа на повторяющиеся сети. Они ограничены по своей природе из-за использования энергетической функции. Симметрично связанные сети со скрытыми сетями известны как машины Больцмана, тогда как сети без скрытой сети известны как сети Хопфилда.
Неконтролируемые предварительно обученные сети: В этой архитектуре мы говорим об отсутствии формального обучения, но сети предварительно обучаются с использованием прошлого опыта. Сюда входят автокодеры, сети глубокого убеждения и генеративные состязательные сети.
Сверточные нейронные сети: Он нацелен на изучение функций более высокого порядка с использованием сверток, что улучшает распознавание изображений и идентификацию пользователей. Благодаря этой архитектуре становится проще распознавать лица, уличные знаки, утконосы и другие объекты.
Рекуррентные нейронные сети: они происходят из семейства каналов прямого распространения, которые верят в отправку своей информации с временными интервалами.
Рекурсивные нейронные сети: Он также отмечает ввод переменной длины. Основное различие между рекуррентным и рекурсивным состоит в том, что первый имеет возможность устройства иерархических структур в наборе обучающих данных, а второй также предоставляет информацию о том, как эта иерархическая структура поддерживается в наборе данных.

Заключение

AI — чрезвычайно мощная и интересная область, которая будет становиться все более повсеместной и важной по мере продвижения вперед и, несомненно, окажет огромное влияние на общество в целом.Эти два метода — одни из очень мощных инструментов ИИ для решения сложных проблем

.

Нейронные сети и глубокое обучение

В этой книге мы сосредоточились на основных принципах нейронных сетей:
как они работают и как их можно использовать для распознавания образов
проблемы. Это материал с множеством непосредственных практических
Приложения. Но, конечно, одна из причин интереса к нейронным сетям.
надежда на то, что однажды они выйдут далеко за рамки такой базовой схемы
проблемы распознавания. Возможно они или какой-то другой подход, основанный на
цифровые компьютеры, в конечном итоге будут использоваться для создания мыслящих машин,
машины, которые соответствуют или превосходят человеческий интеллект? Это понятие далеко
превышает материал, обсуждаемый в книге — или то, что кто-либо в
мир умеет делать.Но рассуждать интересно.

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

Скорее, я исследую здесь вопрос, существует ли
простой набор принципов, которые можно использовать для объяснения
интеллект? В частности, и более конкретно, существует ли
простой алгоритм для интеллекта ?

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

Рассмотрим, например, ранние дни астрономии. Люди знали
издревле существует зверинец объектов в небе:
солнце, луна, планеты, кометы и звезды. Эти
объекты ведут себя по-разному — звезды движутся величественно,
обычный путь по небу, например, в то время как кометы кажутся
из ниоткуда, проносятся по небу, а затем исчезают В 16-м
века только глупый оптимист мог вообразить, что все эти
движения объектов можно объяснить простым набором принципов.Но
в 17 веке Ньютон сформулировал свою теорию универсального
гравитации, которая не только объясняла все эти движения, но и
объяснил земные явления, такие как приливы и поведение
Привязанные к Земле проекты. Глупый оптимист XVI века кажется
оглядываясь назад, как пессимист, просящий слишком мало.

Конечно, в науке таких примеров гораздо больше. Рассмотрим
мириады химических веществ, составляющих наш мир, так красиво
объясняется периодической таблицей Менделеева, которая, в свою очередь, объясняет
по нескольким простым правилам, которые можно получить из квантовой механики.Или загадка того, как много сложностей и разнообразия
биологический мир, происхождение которого, оказывается, лежит в принципе
эволюция путем естественного отбора. Эти и многие другие примеры предлагают
что было бы неразумно исключать простое объяснение
интеллект просто на том основании, что наш мозг — в настоящее время
лучшие образцы интеллекта — делают , кажется,
очень сложно*
* В этом приложении я предполагаю, что для
чтобы компьютер считался интеллектуальным, его возможности должны соответствовать или
превышают человеческие способности мышления.Поэтому я рассмотрю вопрос «Является ли
есть простой алгоритм интеллекта? »как эквивалент« Является ли
есть простой алгоритм, который может «думать» по существу
те же линии, что и человеческий мозг? »Однако стоит отметить, что
вполне могут быть формы интеллекта, не относящиеся к человеческому
думали, но тем не менее интересным образом выходят за рамки этого.

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

Какая из этих двух точек зрения верна?

Чтобы разобраться в этом вопросе, давайте зададим тесно связанный
вопрос, есть ли простое объяснение того, как человеческий
мозги работают.В частности, давайте рассмотрим некоторые способы количественной оценки
сложность мозга. Наш первый подход — это взгляд на
мозг из
коннектомика. это
все о необработанной проводке: сколько нейронов в мозгу,
сколько глиальных клеток и сколько связей между ними
нейроны. Вы, наверное, слышали цифры раньше — мозг
содержит порядка 100 миллиардов нейронов, 100 миллиардов глиальных клеток,
и 100 триллионов связей между нейронами.Эти числа
ошеломляющий. Они также устрашающие. Если нам нужно понять
детали всех этих связей (не говоря уже о нейронах и глиальных
клеток), чтобы понять, как работает мозг, тогда мы
конечно, у нас не будет простого алгоритма для
интеллект.

Есть вторая, более оптимистичная точка зрения, точка зрения на мозг.
из молекулярной биологии. Идея состоит в том, чтобы спросить, сколько генетических
информация необходима для описания архитектуры мозга.Чтобы получить
разобраться с этим вопросом, мы начнем с рассмотрения генетических
различия между людьми и шимпанзе. Вы, наверное, слышали
звучит так, что «люди на 98 процентов шимпанзе». это
поговорка иногда бывает разной — в популярных вариациях также указывается число
как 95 или 99 процентов. Вариации происходят потому, что числа были
первоначально оценено путем сравнения образцов человека и шимпанзе
геномы, а не целые геномы. Однако в 2007 г.
геном шимпанзе был
последовательный
(смотрите также
здесь), а мы
теперь известно, что ДНК человека и шимпанзе различаются примерно на 125 миллионов ДНК.
пар оснований.Это из примерно 3 миллиардов пар оснований ДНК.
в каждом геноме. Поэтому неправильно говорить, что люди на 98 процентов
шимпанзе — мы больше похожи на шимпанзе на 96 процентов.

Сколько информации содержится в этих 125 миллионах пар оснований? Каждая база
пару можно обозначить одним из четырех вариантов — «буквы»
генетического кода, оснований аденина, цитозина, гуанина и
тимин. Таким образом, каждую базовую пару можно описать двумя битами
информация — достаточно информации, чтобы указать один из четырех
этикетки.Итак, 125 миллионов пар оснований эквивалентны 250 миллионам бит.
информации. В этом генетическая разница между людьми и
шимпанзе!

Конечно, эти 250 миллионов бит составляют все генетические
различия между людьми и шимпанзе. Нас интересуют только
разница, связанная с мозгом. К сожалению, никто не знает, что
доля общей генетической разницы необходима для объяснения
разница между мозгами. Но допустим, ради
аргумент, что около половины этих 250 миллионов бит приходится на мозг
различия.Это всего 125 миллионов бит.

125 миллионов бит — впечатляюще большое число. Давайте разберемся
насколько он велик, если перевести его в более человеческие термины. В
в частности, сколько будет эквивалентного количества английского текста?
Это
повороты
выяснилось, что информативность английского текста составляет около 1 бита на
письмо. Звучит низко — в конце концов, в алфавите 26 букв.
— но в английском тексте очень много избыточности.
Конечно, вы можете возразить, что наши геномы тоже избыточны, поэтому два
бит на базовую пару — это завышенная оценка.Но мы проигнорируем это, поскольку
в худшем случае это означает, что мы переоцениваем генетические
сложность. Исходя из этих предположений, мы видим, что генетический
разница между нашим мозгом и мозгом шимпанзе эквивалентна примерно
125 миллионов букв, или около 25 миллионов английских слов. Это о
В 30 раз больше, чем в Библии короля Якова.

Это много информации. Но он не такой уж непонятный.
Это в человеческом масштабе. Может быть, ни один человек никогда не мог понять
все, что написано в этом коде, но группа людей могла бы
понимать это коллективно, через соответствующую специализацию.И
хотя информации много, она ничтожна по сравнению с
информация, необходимая для описания 100 миллиардов нейронов, 100
миллиардов глиальных клеток и 100 триллионов соединений в нашем мозгу. Четный
если мы используем простое, грубое описание — скажем, 10 с плавающей запятой
числа для характеристики каждого соединения — для этого потребуется около
70 квадриллионов бит. Это означает, что генетическое описание является фактором
примерно на полмиллиарда меньше, чем полный коннектом для
человеческий мозг.

Из этого мы узнаем, что наш геном не может содержать
подробное описание всех наших нейронных связей. Скорее он должен
указать только общую архитектуру и базовые принципы, лежащие в основе
мозг. Но эта архитектура и эти принципы кажутся
достаточно, чтобы гарантировать, что мы, люди, вырастем разумными. Из
Конечно, есть нюансы — растущим детям нужны здоровые,
стимулирующая среда и хорошее питание для достижения
интеллектуальный потенциал.Но если мы вырастем в разумных
окружающей среде, здоровый человек будет обладать замечательным интеллектом. В
в каком-то смысле информация в наших генах содержит суть того, как
мы думаем. Более того, принципы, содержащиеся в этом генетическом
информация, вероятно, находится в пределах нашей способности коллективно
схватить.

Все приведенные выше цифры являются очень приблизительными. Возможно, что
125 миллионов бит — это огромное завышение,
более компактный набор основных принципов, лежащих в основе человеческой мысли.Может быть
большая часть из этих 125 миллионов бит — это просто точная настройка относительно незначительных
подробности. Или, может быть, мы были слишком консервативны в том, как мы вычисляли
числа. Очевидно, было бы здорово, если бы это было правдой! Для нашего нынешнего
целей, ключевой момент заключается в следующем: архитектура мозга
сложно, но это не так сложно, как вы думаете
в зависимости от количества связей в мозгу. Мнение
мозг из молекулярной биологии предполагает, что мы, люди, должны когда-нибудь стать
способен понять основные принципы работы мозга
архитектура.

В последних нескольких абзацах я проигнорировал тот факт, что 125 миллионов бит
просто количественно определяет генетическую разницу между человеком и
мозг шимпанзе. Не все функции нашего мозга связаны с этими 125 миллионами
биты. Шимпанзе — сами по себе замечательные мыслители. Может быть
ключ к интеллекту кроется в основном в умственных способностях (и генетических
информация), которая есть у шимпанзе и человека. Если это
правильно, тогда человеческий мозг может быть лишь незначительным обновлением до шимпанзе
мозги, по крайней мере, с точки зрения сложности лежащих в основе
принципы.Несмотря на расхожий человеческий шовинизм насчет наших
уникальные возможности, это немыслимо: шимпанзе и
генетические линии человека разошлись
5
миллион лет назад, это мгновение в эволюционной шкале времени. Однако в
отсутствие более веского аргумента, я сочувствую
обычный человеческий шовинизм: я думаю, что самое интересное
принципы, лежащие в основе человеческой мысли, заключаются в этих 125 миллионах бит, а не в
в той части генома, которую мы разделяем с шимпанзе.

Принятие взглядов на мозг из молекулярной биологии дало нам
сокращение примерно на девять порядков сложности нашей
описание. Хотя это обнадеживает, это не говорит нам о том,
Возможен действительно простой алгоритм интеллекта. Можем ли мы получить
дальнейшее снижение сложности? И, что более важно, можем ли мы
решить вопрос о том, является ли простой алгоритм интеллекта
возможно?

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

Среди свидетельств того, что может существовать простой алгоритм для
интеллект — это эксперимент
сообщил
в апреле 2000 г. в журнале Nature . Команда ученых под руководством
Мриганка Сур «перепрограммировал» мозг новорожденных хорьков. Обычно,
сигнал из глаз хорька передается в часть мозга
известный как зрительная кора.Но за этих хорьков ученые взяли
сигнал из глаз и перенаправил его, чтобы вместо этого
слуховая кора, то есть область мозга, которая обычно используется для
слух.

Чтобы понять, что произошло, когда они это сделали, нам нужно немного знать
о зрительной коре. Зрительная кора содержит много
ориентация
столбцы. Это маленькие пластинки нейронов, каждый из которых отвечает
на визуальные стимулы с определенного направления. Вы можете думать о
столбцы ориентации как крошечные датчики направления: когда кто-то
светит яркий свет с определенного направления, соответствующего
столбец ориентации активирован.Если свет перемещается, другой
столбец ориентации активирован. Один из самых важных высокоуровневых
структур в зрительной коре головного мозга
ориентация
map, которая отображает расположение столбцов ориентации.

Ученые обнаружили, что когда визуальный сигнал от
глаза хорьков были перенаправлены на слуховую кору, слуховую кору
изменилось. Начали появляться столбцы ориентации и карта ориентации.
в слуховой коре. Это было более беспорядочно, чем ориентация
карта обычно находится в зрительной коре, но безошибочно похожа.Кроме того, ученые провели несколько простых тестов того, как хорьки
реагировали на визуальные стимулы, обучая их реагировать по-разному, когда
огни вспыхнули со всех сторон. Эти тесты показали, что
хорьки все еще могли научиться «видеть», по крайней мере, в элементарной
мода, используя слуховую кору.

Это потрясающий результат. Это говорит о том, что есть общие
принципы, лежащие в основе того, как разные части мозга учатся
реагировать на сенсорные данные.Эта общность обеспечивает по крайней мере некоторые
поддержка идеи, что существует набор простых принципов
лежащий в основе интеллект. Однако нам не следует обманывать себя
насколько хорошо было зрение хорьков в этих экспериментах. В
поведенческие тесты проверяли только очень грубые аспекты зрения. И из
Конечно, мы не можем спрашивать хорьков, «научились ли они видеть». Так
эксперименты не доказывают, что перестроенная слуховая кора
давая хорькам визуальное восприятие с высокой точностью.И поэтому они
предоставляют лишь ограниченные доказательства в пользу идеи, что общие
принципы лежат в основе того, как обучаются разные части мозга.

Какие есть доказательства против идеи простого алгоритма для
интеллект? Некоторые данные получены из областей эволюционного
психология и нейроанатомия. С 1960-х гг. Эволюционная
психологи открыли широкий спектр человеческих универсалий ,
сложное поведение, общее для всех людей, в разных культурах и
воспитание.Эти человеческие универсалии включают табу на инцест между
мать и сын, использование музыки и танцев, а также многие сложные
лингвистическая структура, такая как использование нецензурных слов (т. е. табу
слова), местоимения и даже такие простые структуры, как глагол.
Эти результаты дополняют множество свидетельств из
нейроанатомия показывает, что поведение многих людей контролируется
определенные локализованные области мозга, и эти области кажутся
одинаковы у всех людей. Взятые вместе, эти результаты показывают, что
многие очень специализированные модели поведения жестко привязаны к определенным частям
нашего мозга.

Некоторые люди делают вывод из этих результатов, что отдельные объяснения
должны быть необходимы для этих многих функций мозга, и это как
Следствием этого является непреодолимая сложность мозга.
функция, сложность, которая дает простое объяснение
операция (и, возможно, простой алгоритм интеллекта)
невозможно. Например, один известный искусственный интеллект
Исследователь с этой точки зрения — Марвин Мински. В 1970-х и
1980-е годы Мински разработал свою теорию «Общества разума», основанную на
идея о том, что человеческий интеллект — результат большого общества
индивидуально простые (но очень разные) вычислительные процессы, которые
Минский вызывает агентов.В
его книга
описывая теорию, Мински резюмирует то, что он видит как силу
эта точка зрения:

Какой волшебный трюк делает нас умными? Хитрость в том, что есть
нет уловки. Сила интеллекта проистекает из нашего огромного разнообразия,
не по какому-то единственному идеальному принципу.

В ответ *
* В книге «Созерцая умы: форум для
Искусственный интеллект «, под редакцией Уильяма Дж. Кланси, Стивена
В. Смоляр и Марк Стефик (MIT Press, 1994).к отзывам о его
книга, Мински подробно остановился на мотивации Общества Разума,
приводя аргумент, аналогичный приведенному выше, на основе нейроанатомии
и эволюционная психология:

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

Мински, конечно, не единственный, кто придерживается точки зрения
по этим линиям; Я просто привожу его в пример сторонника
этой аргументации. Я считаю этот аргумент интересным, но не
считаю, что доказательства убедительны. Хотя это правда, что мозг
состоит из большого количества разных регионов, с разными
функций, из этого не следует, что простое объяснение
функция мозга невозможна. Возможно, эти архитектурные
различия возникают из общих основополагающих принципов, так же как
движение комет, планет, Солнца и звезд — все возникает из
единая гравитационная сила.Ни Минский, ни кто-либо еще не спорил
убедительно против таких основополагающих принципов.

Мое собственное предубеждение в пользу существования простого алгоритма для
интеллект. И главная причина, по которой мне нравится эта идея, сверх того
приведенные выше (неубедительные) аргументы заключаются в том, что это оптимистическая идея.
Когда дело доходит до исследований, необоснованного оптимизма часто бывает больше.
продуктивно, чем, казалось бы, лучше обоснованный пессимизм, для
Оптимист имеет мужество начинать и пробовать новое.Это
путь к открытию, даже если обнаруженное, возможно, не то, что было
изначально надеялся. Пессимист может быть более «правым» в узком
смысл, но откроет меньше, чем оптимист.

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

С учетом всего сказанного, в его наиболее оптимистичной форме я не
верю, что мы когда-нибудь найдем простой алгоритм интеллекта.Быть
более конкретно, я не верю, что мы когда-нибудь найдем действительно короткий Python
(или C, или Lisp, или что-то еще) — скажем, где угодно до
тысячи строк кода, который реализует искусственный интеллект.
Я также не думаю, что мы когда-нибудь найдем действительно легко описываемый нейронный
сеть, которая может реализовать искусственный интеллект. Но я верю
стоит действовать так, как будто мы можем найти такую ​​программу или сеть.
Это путь к пониманию, и, следуя по этому пути, мы можем однажды
понимать достаточно, чтобы написать более длинную программу или построить более
сложная сеть, которая действительно демонстрирует интеллект.И так это
стоит действовать как чрезвычайно простой алгоритм для интеллекта
существуют.

В 1980-х годах выдающийся математик и ученый-компьютерщик
Джек Шварц
был приглашен на дебаты между сторонниками искусственного интеллекта и
скептики искусственного интеллекта. Дискуссия стала неуправляемой,
сторонники, делающие чрезмерные заявления об удивительных вещах, просто
за углом, и скептики удваивают свой пессимизм,
утверждать, что искусственный интеллект был совершенно невозможен.Шварц
был сторонним наблюдателем в дебатах и ​​промолчал, поскольку обсуждение
нагрелся. Во время затишья его попросили выступить и высказать свое мнение.
мысли по обсуждаемым вопросам. Он сказал: «Ну, некоторые
эти разработки могут оказаться за сотней Нобелевских премий »
(см. стр. 22).
Мне это кажется идеальным ответом. Ключ к искусственному интеллекту
простые, мощные идеи, и мы можем и должны искать оптимистично
за эти идеи. Но нам понадобится много таких идей, и мы
еще предстоит пройти долгий путь!

.

Нейронные сети и глубокое обучение

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

Автоматическое обучение на основе данных звучит многообещающе. Однако пока
2006 мы не знали, как обучить нейронные сети, чтобы превзойти больше
традиционные подходы, за исключением нескольких специализированных задач. какой
в 2006 году изменилось открытие методов обучения в
так называемые глубокие нейронные сети. Эти методы теперь известны как
глубокое обучение. Они получили дальнейшее развитие, и сегодня глубокие нейронные
сети и глубокое обучение обеспечивают выдающуюся производительность во многих
важные проблемы компьютерного зрения, распознавания речи и естественного
языковая обработка.Они развертываются в больших масштабах
такие компании, как Google, Microsoft и Facebook.

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

Принципиально-ориентированный подход

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

Это означает, что книга категорически не является руководством по использованию некоторых
конкретная библиотека нейронной сети. Если вы в основном хотите выучить свой
в библиотеке, не читайте эту книгу! Найдите нужную библиотеку
изучать и работать с учебными пособиями и документацией. Но будь
предупреждал.Хотя это дает немедленное решение проблем, если вы
хотите понять, что на самом деле происходит в нейронных сетях, если вы
хотите получить информацию, которая будет актуальна и годы спустя, тогда это
недостаточно просто изучить какую-нибудь горячую библиотеку. Вы должны понимать
прочное и прочное понимание того, как работают нейронные сети.
Технологии приходят и уходят, но понимание — навсегда.

Практический подход

Мы изучим основные принципы нейронных сетей и
обучение путем атаки на конкретную проблему: проблема обучения
компьютер для распознавания рукописных цифр.Эта проблема крайне
сложно решить с помощью обычного подхода к программированию.
И все же, как мы увидим, ее можно довольно хорошо решить, используя простой
нейронная сеть с несколькими десятками строк кода и без специальных
библиотеки. Более того, мы улучшим программу через множество
итераций, постепенно включающих все больше и больше основных идей
о нейронных сетях и глубоком обучении.

Этот практический подход означает, что вам понадобится программирование.
опыт чтения книги.Но не нужно быть профессионалом
программист. Я написал код на Python (версия 2.7), который,
даже если вы не программируете на Python, это должно быть легко понять с
просто немного усилий. По ходу книги мы будем развивать
небольшую библиотеку нейронных сетей, которую вы можете использовать для экспериментов и
чтобы построить понимание. Весь код доступен для скачивания
Вот.
Когда вы дочитаете книгу или прочтете, вы легко сможете выбрать
одну из наиболее полнофункциональных библиотек нейронных сетей, предназначенных
для использования в производстве.

Кстати, математические требования для чтения книги:
скромный. В большинстве глав есть немного математики, но обычно
просто элементарная алгебра и графики функций, которых я ожидаю больше всего
читатели будут в порядке. Иногда я использую более продвинутые
математике, но структурировали материал так, чтобы вы могли
если некоторые математические детали ускользают от вас. Одна глава, в которой
более тяжелая математика — это глава 2, которая
требует небольшого многомерного исчисления и линейной алгебры.Если те
не знакомы, я начинаю главу 2 с
обсуждение того, как ориентироваться в математике. Если ты найдешь это
действительно тяжелый, вы можете просто перейти к
резюме
основные результаты главы. В любом случае не о чем беспокоиться
это в самом начале.

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

.

Введение в глубокое обучение и нейронные сети — глубокое обучение для новичков (1) | автор: Науа Канг

Добро пожаловать в первую публикацию моей серии «Глубокое обучение для новичков », написанную мной, новичком. Я пишу как стратегию обучения с подкреплением , чтобы лучше обрабатывать и усваивать знания. Но если вы новичок в области глубокого обучения, то это также для вас, потому что мы можем учиться вместе, как новички !

( Вы также можете прочитать этот пост на моем сайте , который поддерживает LaTeX с MathJax )

Источник: deepinstinct.com

Глубокое обучение, вероятно, сейчас является одной из самых горячих тем в сфере технологий. Как крупные корпорации, так и молодые стартапы стремятся к тому, чтобы в этой модной сфере лихорадка. Если вы считаете, что большие данные важны, вам следует позаботиться о глубоком обучении. The Economist говорит, что данные — это новая нефть в 21 веке. Если данные — это сырая нефть, базы данных и хранилища данных — это буровые установки, которые копают и перекачивают данные в Интернете, тогда думайте о глубоком обучении как о нефтеперерабатывающем заводе, который, наконец, превращает сырую нефть во все полезные и полезные конечные продукты.Под землей может быть спрятано много «ископаемого топлива», и на рынке есть много буровых установок и насосов, но без правильных инструментов для нефтепереработки вы не получите ничего ценного. Вот почему так важно глубокое обучение. Это часть общей картины, основанной на данных.

Хорошая новость в том, что у нас не будет исчерпания данных, и наша «машина переработки» становится все лучше и лучше. Сегодня данные генерируются практически при любых действиях в сети. Так что данные, в отличие от нефти, «устойчивы» и «стремительно растут».Между тем, пока данные не попадают в мусор, глубокое обучение не дает мусора. Следовательно, чем больше данных, тем лучше. (Ознакомьтесь с публикацией Трента МакКонаги о блокчейнах для ИИ как о решении проблемы репутации данных!).

Также этот «нефтеперерабатывающий завод» совершенствуется как в программном, так и в аппаратном отношении. Алгоритмы глубокого обучения улучшились за последние несколько десятилетий, и разработчики по всему миру внесли свой вклад в такие фреймворки с открытым исходным кодом, как TensorFlow, Theano, Keras и Torch, которые позволяют людям легко создавать алгоритмы глубокого обучения, как если бы они играли с деталями LEGO. .И благодаря спросу со стороны геймеров по всему миру графические процессоры (графические процессоры) позволяют нам использовать алгоритмы глубокого обучения для создания и обучения моделей с впечатляющими результатами в кратчайшие сроки! Итак, ко всем родителям, которым не нравятся ваши дети, играющие в игры: у игр есть свои преимущества…

Вы, наверное, читали новости и знаете, что глубокое обучение — это секретный рецепт многих захватывающих разработок, благодаря которым многие из наших сбываются самые смелые мечты и, возможно, кошмары.Кто бы мог подумать, что AlphaGo DeepMind сможет победить Ли Седола, одного из лучших игроков в Го, в самой глубокой настольной игре, которая может похвастаться большим количеством возможных ходов, чем атомов во всей вселенной? Многие люди, в том числе и я, никогда этого не предвидели. Это казалось невозможным. Но он сейчас здесь. Глубокое обучение побеждает нас в самой сложной настольной игре. Когда пробуждается ИИ? Некоторые думают, что скоро будет.

Ли Седол против AlphaGo в 2016 году, Источник: The New Yorker

. Мы не говорили о других впечатляющих приложениях, основанных на глубоком обучении, таких как Google Translate и автономное вождение Mobileye.Вы называете это. Не забыл ли я упомянуть, что глубокое обучение также побеждает врачей в диагностике рака? Глубокое обучение отлично справляется со многими задачами с меньшим количеством ошибок, чем у людей! Это не только автоматизация скучных вещей, но и забавных вещей. Эх, мы земные люди…

Уважаемый господин Президент, это не иностранцы. Это автоматизация.

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

  1. Идентификация лиц (или, в более общем смысле, категоризация изображений)
  2. Чтение рукописных цифр и текстов
  3. Распознавание речи (больше не нужно самостоятельно расшифровывать интервью)
  4. Перевести языки
  5. Играть в компьютерные игры
  6. Управлять беспилотными автомобилями (и другими типами роботов)

И многое другое.Просто сделайте паузу на секунду и представьте себе все, чего можно достичь с помощью глубокого обучения. Это потрясающе и, возможно, немного страшно!

Ладно, подожди секунду. Вероятно, вы видели такие термины, как искусственный интеллект ( AI ), машинное обучение ( ML ) и глубокое обучение ( DL ), которые повсюду летают в вашей ленте новостей в социальных сетях. В чем разница между ними? Они означают одно и то же или что? Отличный вопрос. Прежде чем мы углубимся в глубокое обучение, важно постепенно выстроить концептуальную основу этих жаргонов.

Грубо говоря, приведенный ниже график демонстрирует взаимосвязь этих трех концепций. Глубокое обучение — это подраздел машинного обучения, а машинное обучение — это подраздел искусственного интеллекта. И Офир Самсон, и Карлос Э. Перес написали о них хорошие рассказы. Проверьте здесь и здесь.

Источник: Nvidia

Давайте сначала обсудим всеохватывающий ИИ. Вы, наверное, уже знакомы с тестом Тьюринга . Компьютер проходит тест Тьюринга, если человек, задав ему несколько письменных вопросов, не может определить, исходят ли письменные ответы от другого человека или от компьютера.Согласно Искусственный интеллект: современный подход , Питер Норвиг и Стюарт Рассел определяют 4 способности, которыми компьютер должен обладать, чтобы пройти тест Тьюринга:

  • Обработка естественного языка: для успешного общения на английском языке
  • Знания Представление: для хранения того, что компьютер читает
  • Автоматическое рассуждение: для использования сохраненных знаний для ответа на вопросы и создания новых выводов
  • Машинное обучение: для адаптации к новым обстоятельствам и определения новых шаблонов

А, есть термин «машинное обучение»! ML — это обучение алгоритмов обучения, таких как линейная регрессия, KNN, K-средние, деревья решений, случайный лес и SVM с наборами данных, чтобы алгоритмы могли научиться адаптироваться к новой ситуации и находить шаблоны, которые могут быть интересными и важными.Опять же, ML управляется данными. Много странных терминов по алгоритмам обучения? Не волнуйтесь, я их тоже не знаю. Так что в будущем мы будем учиться вместе.

Для обучения машинному обучению набор данных можно пометить, например он поставляется с «листом ответов», сообщающим компьютеру, какой правильный ответ, например, какие электронные письма являются спамом, а какие нет. Это называется контролируемым обучением , и такие алгоритмы, как линейная регрессия и KNN, используются для такой контролируемой регрессии или классификации .Другие наборы данных могут быть не помечены, и вы буквально говорите алгоритму, например, K-Means, чтобы связал или кластер шаблонов, которые он находит без какого-либо листа ответов. Это называется обучение без учителя . Вот отличный ответ на вопрос о контролируемом и неконтролируемом обучении в Stack Overflow, а также статья о контролируемом и неконтролируемом обучении из блога Оливии Клозе.

Источник: http://oliviaklose.com/

Норвиг и Рассел также упоминают другой тест под названием Total Turing Test , который дополнительно исследует способности восприятия компьютера с помощью физического моделирования.Чтобы пройти его, компьютеру необходимы:

  • Компьютерное зрение: для восприятия объектов в окружающей среде
  • Робототехника: для управления объектами и перемещения вокруг

Так что насчет DL сейчас? Помните общие задачи, с которыми глубокое обучение способно справиться из раздела выше? Такие вещи, как распознавание лиц или рукописного текста, связаны с компьютерным зрением, потому что вы загружаете графику в компьютер для анализа. Другие задачи, такие как языковой перевод или распознавание речи, связаны с обработкой естественного языка (NLP).Таким образом, DL является подветвью ML в том смысле, что в нем также есть набор алгоритмов обучения, которые могут обучаться и учиться на данных, а более конкретно DL питается от нейронных сетей . Более того, DL может работать вне области машинного обучения и помогает другим областям, таким как компьютерное зрение и НЛП, так что, надеюсь, ИИ однажды сможет пройти тест Тьюринга и общий тест Тьюринга!

Но что такое нейронная сеть? Имитирует ли это поведение реальных нейронных клеток? Или это какой-то волшебный черный ящик? Некоторым из вас представленная информация может показаться чрезмерной, поэтому давайте сделаем перерыв и проверим несколько бесплатных онлайн-ресурсов, чтобы узнать, что вам подходит 🙂 После этого мы сразу перейдем к нейронным сетям.

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

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

  1. Нейронные сети и глубокое обучение Майкла Нильсена
  2. Нейронные сети Джеффри Хинтона для машин Обучение
  3. Глубокое обучение Гудфеллоу, Бенжио и Курвилля
  4. Глубокое обучение Яна Траска,
  5. Глубокое обучение Франсуа Шолле с помощью Python
  6. Наностепень глубокого обучения Udacity (не бесплатно, но высокого качества)
  7. Глубокое обучение Udemy AZ (10–15 долларов США) )
  8. Стэнфордские CS231n и CS224n
  9. Канал Сираджа Раваля на YouTube

Список можно продолжать и продолжать.У Дэвида Вентури есть пост на freeCodeCamp, в котором перечислены многие другие ресурсы. Посмотрите здесь.

Мы действительно счастливы в эпоху самообразования. Кстати, вы слышали о старшекласснике Абу Кадере из Чикаго? Этот ребенок сам обучился машинному обучению и Tensorflow, структуре глубокого обучения, и помог улучшить диагностику рака груди до 93% -99% точности в реальном времени! Он был представлен на Google I / O 2017. Ниже приводится вдохновляющее видео с его историей от Google.

Источник: Google

Хорошо, я надеюсь, что история Абу Кадера вас вдохновит! Давайте перейдем ко второй основной теме этой публикации: введение в нейронные сети.Древний китайский философ Лао-цзы однажды сказал:

«Путешествие в тысячу миль начинается с одного шага».

Итак, мы начнем и закончим этот пост с очень простой нейронной сети. Звучит круто? Вундербар.

Несмотря на свою недавно обретенную известность, нейронные сети совсем не новы. В 1958 году американский психолог Фрэнк Розенблатт попытался построить «машину, которая чувствует, распознает, запоминает и реагирует, как человеческий разум» и назвал машину Perceptron .Но Розенблатт не изобрел перцептроны из воздуха. Собственно, он стоял на плечах гигантов и был вдохновлен предыдущими работами Уоррена Маккалока и Уолтера Питтса 1940-х годов. Черт возьми, это делает нейронные сети или, точнее, перцептрон, динозавром в этом быстро меняющемся мире технологий.

Розенблатт и перцептрон, Источник: The New Yorker

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

Первоисточник: thinglink.comA Single Perceptron

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

  1. С левой стороны у вас есть нейроны (маленькие кружки) x с индексами 1, 2,…, m , несущие входных данных.
  2. Мы умножаем каждый входной сигнал на вес w, также помеченный индексами 1, 2,…, m , вдоль стрелки (также называемой синапсом ) до большого круга в середине. Итак, w1 * x1 , w2 * x2 , w3 * x3 и так далее.
  3. После того, как все входные данные умножены на вес, мы суммируем их все и добавляем еще одно заранее определенное число, называемое смещением .
  4. Затем сдвигаем результат вправо.Теперь у нас есть ступенчатая функция в прямоугольнике. Это означает, что если результат шага 3 — любое число, равное или большее 0, тогда мы получаем 1 как выход, иначе, если результат меньше 0, мы получаем 0 как выход.
  5. Выход либо 1, либо 0.

Обратите внимание, что в качестве альтернативы, если вы переместите смещение в правую часть уравнения в функции активации, например, sum (wx) ≥ -b , то это -b называется пороговым значением .Таким образом, если сумма входных данных и весов больше или равна пороговому значению, то активация вызывает 1. В противном случае результат активации равен 0. Выберите то, что поможет вам лучше понять, поскольку эти два способа представления взаимозаменяемы.

Иллюстрация использования порогового значения вместо смещения

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

Процедуры персептрона, отмеченные цветами

  1. Входы — это подается в персептрон
  2. Веса умножаются на каждый вход
  3. Суммирование и затем прибавляется смещение
  4. Применяется функция активации .Обратите внимание, что здесь мы используем ступенчатую функцию, но есть и другие более сложные функции активации, такие как сигмоид , гиперболический тангенс (, ), выпрямитель (, ) и другие . Не беспокойтесь, мы рассмотрим многие из них в будущем!
  5. Выход либо запускается как 1, либо нет, как 0. Обратите внимание, что мы используем y hat для маркировки выходных данных, созданных нашей моделью персептрона

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

Упрощенное представление персептрона

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

Для понимания перцептронов давайте рассмотрим очень простой пример, который не обязательно является реалистичным.Предположим, вы очень заинтересованы после прочтения моего поста и вам нужно решить, изучать DL или нет . На ваше решение влияют 3 фактора:

  1. Если вы заработаете больше денег после освоения DL (Да: 1, Нет: 0)
  2. Просты ли соответствующие математика и программирование (Да: 1, Нет: 0)
  3. Вы можете работать с DL сразу без необходимости в дорогостоящем графическом процессоре (Да: 1, Нет: 0)

Мы используем x1, x2, и x3 в качестве входных переменных для каждого из этих факторов и присваиваем двоичное значение (1 или 0) каждому из них, поскольку ответ просто да или нет.Предположим, вам действительно нравится DL, и вы готовы преодолеть свой пожизненный страх перед математикой и программированием. И у вас также есть небольшая экономия, инвестирующая сейчас в дорогой графический процессор Nvidia для обучения ваших моделей DL. Предположите, что эти два фактора одинаково менее важны, поскольку вы можете пойти на компромисс. Однако вы действительно хотите заработать больше денег, потратив так много времени и сил на изучение DL. Таким образом, с высокими ожиданиями возврата инвестиций, если вы не сможете заработать больше $$$ впоследствии, вы не будете тратить свое драгоценное время на DL.

Понимая свои предпочтения в принятии решений, предположим, что у вас есть 100% вероятность заработать больше денег после изучения DL, потому что на рынке большой спрос при очень небольшом предложении. Итак, x1 = 1 . Скажем, математика и программирование очень сложны. Итак, x2 = 0 . Наконец, допустим, у вас должен быть мощный графический процессор, такой как Titan X. Итак, x3 = 0 . Хорошо, у нас есть готовые входы, и мы также можем инициализировать веса. Возьмем w1 = 6, w2 = 2, w3 = 2 . Чем больше вес, тем большее влияние имеет соответствующий вход . Итак, поскольку вы больше всего цените деньги за свое решение изучать DL, w1> w2 и w1> w3 .

Предположим, что пороговое значение threshold = 5, , что эквивалентно тому, что член смещения bias = -5 . Мы складываем все это и добавляем смещение. Проверьте следующее, чтобы определить, будете ли вы изучать DL с помощью перцептрона.

Обратите внимание, что с пороговым значением 5 мы будем изучать глубокое обучение, только если заработаем больше денег.Даже если обе математические операции просты ( x2 = 1 ) и вам не нужно тратить деньги на покупку графического процессора ( x3 = 1 ), вы все равно не изучите DL, если вы не сможете заработать больше денег позже. См. Иллюстрацию ниже:

Теперь вы знаете фокус со смещением / порогом. Этот высокий порог 5 означает, что ваш доминирующий фактор должен быть удовлетворен, чтобы персептрон инициировал выход 1. В противном случае выход будет 0.

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

  1. После этого вы заработаете больше денег, поэтому x1 = 1 гарантирует ваше решение изучить DL независимо от значений x2 и x3
  2. Или, математика проста, а вы не делаете Необязательно покупать графический процессор, поэтому x2 = x3 = 1 также гарантирует, что вы решите изучить DL независимо от значения x1

Как так? Вы, наверное, уже знаете;) Ниже объяснение:

Ага.Теперь порог ниже, поэтому два других фактора могут мотивировать вас изучать DL, даже если ваша перспектива зарабатывать больше денег исчезла. Теперь я рекомендую вам поиграть с весами w1, w2 и w3 и посмотреть, как ваше решение об изучении DL изменится соответственно!

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

В реальной модели DL нам даны входные данные, которые мы не можем изменить. Между тем, термин смещения инициализируется перед обучением модели нейронной сети. Итак, предположим, что мы предполагаем, что смещение равно 7. Теперь предположим следующие входные данные, так что (1). вы заработаете больше денег, (2). математика и программирование для DL будут сложными, и (3). да, вам нужно потратить 1400 долларов на графический процессор для работы с DL, и , что наиболее важно, мы предполагаем, что вы действительно хотите изучить глубокое обучение, , который мы назовем желаемый результат для того, как в идеале персептрон должен правильно предсказывать или определять :

Предположим далее, что наши веса инициализируются следующим образом:

Итак, с входными данными, смещением и выходной меткой (желаемый результат):

Хорошо, мы знайте, что фактический результат работы вашей нейронной сети отличается от вашего реального решения изучать DL.Так что же должна делать нейронная сеть, чтобы учиться и совершенствоваться, учитывая разницу между фактическим и желаемым результатом? Да, мы не можем изменить входные данные, и теперь мы инициализировали нашу предвзятость. Итак, единственное, что мы можем сделать, это сказать перцептрону, чтобы он регулировал веса! Если мы скажем персептрону увеличить w1 до 7, не изменяя w2 и w3 , тогда:

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

Между прочим, теперь, когда мы закончили наш не очень реалистичный пример, я могу сказать вам, что вам не нужно покупать графический процессор. Если вы начинаете тренировать небольшие наборы данных, вам, скорее всего, не понадобится графический процессор. Однако вы можете использовать облачные сервисы, такие как AWS, Floyd и, возможно, Google TPU) вместо реального графического процессора, когда вы начинаете обучать большие наборы данных с большим количеством файлов изображений.

Кроме того, математика для DL непроста, но и не является непреодолимой. В большинстве случаев мы просто столкнемся с некоторыми матричными операциями и базовыми вычислениями. Но помните, ничему, что вас выделяет, не легко научиться. Вот цитата из Talent is Overated :

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

Итак, для тех из вас, кто боится математики и программирования, как я, надеюсь, эта цитата придаст вам смелости продолжать учиться и практиковаться 🙂

Несмотря на некоторые ранние сенсации общественности, популярность персептрона исчезла тихо из-за его ограничений. В 1969 году Марвин Мински и Сеймур Паперт обсудили эти ограничения, в том числе неспособность перцептрона изучить вентиль XOR (исключающее ИЛИ) (так что в основном однослойный перцептрон со ступенчатой ​​функцией не может понять логику того, что погода должна быть либо горячим, либо холодным, но не одновременно).И эти логические вентили, такие как И, ИЛИ, НЕ, XOR, являются очень важными концепциями, которые питают ваш компьютер;) TutorialsPoint имеет список логических вентилей, если вы хотите узнать больше. Проверить здесь.

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

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

Источник: mathnotes.org

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

Что !? Так что же такое линейная комбинация ? И почему перцептрон не может изучить ворота XOR? Теперь это сбивает с толку.Хорошо, вот объяснение:

Задумайтесь на минутку о нашем предыдущем примере. С 3 бинарными входами для определения того, зарабатываете ли вы больше денег после изучения DL, если математика и программирование легки или нет, и если вы можете изучать DL, не вкладывая средства в дорогостоящее оборудование, у нас в общей сложности 2³ = 8 возможных наборов входы и результаты. С весами ( w1 = 6, w2 = 2, w3 = 2), и смещением = -5, у нас есть следующая таблица для набора ( x1, x2, x3 ):

  1. (1 , 0, 0) -> сумма + смещение = 6–5 = 1, желаемый результат = 1
  2. (1, 1, 0) -> сумма + смещение = 8–5 = 3, желаемый результат = 1
  3. (1 , 1, 1) -> сумма + смещение = 10–5 = 5, желаемый результат = 1
  4. (1, 0, 1) -> сумма + смещение = 8–5 = 3, желаемый результат = 1
  5. (0 , 1, 1) -> сумма + смещение = 4–5 = -1, желаемый результат = 0
  6. (0, 1, 0) -> сумма + смещение = 2–5 = -3, желаемый результат = 0
  7. (0, 0, 1) -> сумма + смещение = 2–5 = -3, желаемый результат = 0
  8. (0, 0, 0) -> сумма + смещение = 0–5 = -5, желаемый результат = 0

Итак, буквально, если мы начнем со случайных весов, отличных от ( w1 = 6, w2 = 2, w3 = 2 ), наш перцептрон попытается научиться регулировать и найти идеальные веса ( w1 = 6 , w2 = 2, w3 = 2 ), что будет правильно соответствовать фактическому выходу каждого набора ( x1, x2, x3 ) на желаемый результат.Фактически, мы можем разделить эти 8 возможных наборов в трехмерном пространстве с помощью плоскости, такой как плоскость x1 = 0,5 . Этот тип проблемы классификации, при которой вы можете нарисовать плоскость для разделения различных выходных данных (или нарисовать линию для выходных данных в 2D), является проблемой, которую может решить наш однослойный перцептрон.

Плоскость, разделяющая 4 набора слева от 4 справа Плоскость, отделяющая 4 набора слева от 4 справа

Я надеюсь, вы можете представить себе плоскость, разделяющую 8 наборов входных данных выше.Поскольку наборы ( x1, x2, x3 ) включают трехмерное пространство, это может быть немного сложно. Но в целом однослойный персептрон с линейной функцией активации может научиться разделять набор данных, как на диаграмме A на графике ниже, которая отделяется линией y = ax + b . Но если набор данных разделен только нелинейным кругом, как на диаграмме B, наш перцептрон будет работать ужасно.

Источник: Себастьян Рашка

Почему так? Я копирую для вас цитату из Stack Overflow.Вы также можете найти ответ здесь.

«Функции активации не могут быть линейными, потому что нейронные сети с линейной функцией активации эффективны только на один уровень, независимо от сложности их архитектуры. Вход в сети обычно является линейным преобразованием (вход * вес), но реальный мир и проблемы нелинейны. Чтобы сделать поступающие данные нелинейными, мы используем нелинейное отображение, называемое функцией активации. Функция активации — это функция принятия решений, которая определяет наличие определенной нейронной функции.Он отображается между 0 и 1, где ноль означает, что функция отсутствует, а единица означает, что функция присутствует. К сожалению, небольшие изменения, происходящие в весах, не могут быть отражены в значении активации, потому что оно может принимать только 0 или 1. Следовательно, нелинейные функции должны быть непрерывными и различаться в этом диапазоне. Нейронная сеть должна иметь возможность принимать любой входной сигнал от -infinity до + infinite, но она должна иметь возможность отображать его на выход, который находится в диапазоне от {0,1} или в некоторых случаях от {-1,1} — таким образом, необходимость активации функции.Нелинейность необходима в функциях активации, потому что ее цель в нейронной сети состоит в том, чтобы создать нелинейную границу принятия решения посредством нелинейных комбинаций веса и входных данных ». -user7479

Так почему же однослойный персептрон со ступенчатой ​​функцией не может изучить вентиль XOR? Посмотрите на график ниже. Слева — логическая диаграмма XOR, а справа — декартово представление двух различных результатов (1 и 0) от элемента XOR.

Источник: https://stackoverflow.com/a/35919708/6297414

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

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

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

Следующим будет новый пост о нейронных сетях с скрытыми слоями (звучит забавно, правда?) И новой функцией активации, называемой сигмоидной функцией . Если позволяет пространство, мы коснемся градиентного спуска, и обратного распространения ошибки, , которые являются ключевыми концепциями для изучения интеллектуальной нейронной сети.Следите за обновлениями (вот ссылка на второй пост) 🙂

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

.

Leave a Comment

Ваш адрес email не будет опубликован. Обязательные поля помечены *