В началото беше невронът: разбиране на градиентно спускане, обратно разпространение, линейна регресия, логистична регресия, автоенкодери, конволюционни невронни мрежи и VGG16. С визуални помощни средства и практическо кодиране в Python & Keras.

Тази статия е за тези, които пропускат безболезненото пътуване през черната кутия на дълбокото обучение. Ние мотивираме и ангажираме читателите с една история за фермер, който се е грижил твърде много за бъдещето. Започваме да разглеждаме неговите проблеми, като решаваме проста линейна и логистична регресия с помощта на изкуствена невронна мрежа. Ние постепенно изграждаме нашето разбиране, като разглеждаме градиентно спускане, верижно правило и обратно разпространение. По-късно се задълбочаваме, като изграждаме автоенкодер и добавяме конволюционни слоеве, за да обезшумим MNIST ръчно написани цифри. Освен това извличаме функции от предварително обучената мрежа VGG16, след като обяснихме защо такива мрежи са толкова успешни в компютърното зрение.

Като прочетете тази статия, вие най-накрая ще разгадаете мистерията на дълбокото обучение.

Ще имате и смислени отворени въпроси. Това е целият смисъл на (задълбоченото) обучение, нали?

Да започнем с една история.

Човекът, който живееше в бъдещето

Това е историята на един възрастен човек, който иска да знае за бъдещето си. Той беше фермер. Беше негово щастие да има полета, произвеждащи все по-голямо количество реколта всяка година. Той имаше твърде много от него в житниците си и трябваше да предложи излишъка на своите приятели и съседи. Все пак се тревожеше за бъдещето. Не знаеше колко да даде за благотворителност и колко да задържи. Всъщност това зависи от това колко ще прибере през следващите години. Имаше нужда от точна прогноза за производството през следващите години.

И така, каква е връзката с дълбокото обучение? Моля, продължавайте да четете и ще се зарадвате. Най-големият син на фермера излезе със следния експеримент. Той взел проби от зърно и поставил в торба количество, съответстващо приблизително на големината на реколтата за всяка от предходните години. Всяка чанта представлява година във възходящ ред на времето. След това той моли най-малкия си брат или сестра да постави пръчка на върха на торбите, така че пръчката да не падне и да е добре балансирана, както е показано на снимката, включваща тази статия.

Това изображение даде на стареца представа за реколтата, която можеше да очаква през следващите години, ако приемем, че тенденцията се запази със същото темпо. Дали синът му току-що беше изобретил линейната регресия, стотици години преди Франсис Галтън (съжалявам, сър)?

Ако можем да направим линейна регресия, защо се нуждаем от изкуствени невронни мрежи?

Продължете да четете, скоро ще се заемем с дълбокото обучение. Хората са обсебени от бъдещето. Искаме да знаем дали утре ще вали, дали ще се оженим догодина, дали и кога най-накрая ще забогатеем. В миналото това бяха любимите въпроси, задавани на оракулите (не на софтуерната компания Oracle). Предполага се, че оракулите са били хора със специални умения, които биха предсказвали бъдещето въз основа на реални данни като линии в ръката, съзвездие от звезди или вкус на кръв.

Да можеш да предскажеш бъдещето не винаги е нещо добро. Касандра от Троя имаше дарбата да предвижда. За нейно собствено зло тя беше прокълната от Аполон, че никой няма да повярва на нейните предсказания. Следователно нейните предупреждения за унищожаването на Троя бяха пренебрегнати и нещата не се развиха добре за нея. Днес компании, организации и правителства търсят своя собствена Касандра от Троя, като наемат специалисти по данни, оракули на съвременното време. Тъй като някои изследователи на данни и машинни обучаващи се искат да бъдат възможно най-неясни, за да придобият по-голяма важност, като оракули от миналото, те избират да използват така наречената технология Deep Learning през цялото време . Освен това, защото работи. Не само за предсказване на бъдещето, но и за разбиране на настоящето, правене на изводи и класифициране на всякакви неща. Можете да погледнете тази статия, за да видите сами какви невероятни неща можем да направим с дълбокото обучение.

Защо дълбокото обучение работи? Защо синът на нашия фермер ще има нужда от задълбочено обучение, въпреки че вече е изобретил линейната регресия? Това са въпроси, които ще се опитаме да разгледаме в следващите раздели.

Линейна регресия с неврон

Първо ще разгледаме линейния модел на сина на фермера. Той използва годината като предсказател на количеството реколта (нейната величина). Чрез начертаване на възможно най-добрата съвпадаща линия, която следва тенденцията на количеството през годините, той успя да предвиди количеството на реколтата за следващите години. Математически той намери линия Ŷза години X с пресечна точка β0и наклон β1.

Аналитично решение на линейна регресия

Като се имат предвид измерванията в реалния свят за Y и съответния предиктор X, можем да изчислим наклона и пресечната точка, както следва.

Едно изображение струва хиляда думи, както и кодът на Python. За да направим красиви графики и да изследваме модела, ще пресъздадем данните, използвани от сина на фермера. Нека създадем 100 изкуствени набора от случайни измервания по правата линия в равнина, представена от линейното уравнение. Ние разпределяме тези точки по линията равномерно в интервала между -2 и 3. След това добавяме произволна нормално разпределена стойност със стандартно отклонение 1 и средно 0 към всяка Y стойност. Накрая използваме формулата по-горе, за да изчислим пресечната точка и наклона.

Както можем да видим на изображението по-горе, идеята за сина на фермера е печеливша. Можем да предвидим Y за всяка стойност на X, тъй като знаем регресионната линия, която диктува поведението на Y. И така, можем ли да направим същото с изкуствена невронна мрежа? Първо, трябва да дефинираме какво всъщност е изкуствена невронна мрежа.

Биологичният неврон

Какво дойде първо? Неврология или изкуствени невронни мрежи? Както и да е, идеята за изкуствен неврон изглежда идва от невроните в главата ни. Нашият мозък е изграден от 100 милиарда неврони. Когато електрическите сигнали преминават през дендритите в ядрото на неврона, се натрупва електрически заряд. Когато клетката достигне определено ниво на заряд, праг, тя се активира, изпращайки електрически сигнал през аксона. Невроните претеглят различните входящи сигнали по различен начин, когато решават кога да задействат. Някои смятат, че изкуствените невронни мрежи имитират процеса на присвояване на различни тегла на различни дендрити (входове).

Изкуственият неврон

Единичен изкуствен неврон приема вход X, прилага (линейна) афинна трансформация с помощта на теглаW, за да създаде временна стойност h. След това предава тази стойност през функция за активиране, за да произведе изход. В нашия пример за линейна регресия X може да бъде число, да речем 2. Афинната трансформация ще използва пресечната точка и наклона, съхранени във вектора W, за да трансформира входа, в ред за връщане, да кажем h=5. По-късната стойност ще премине през активиране, което е линейна функция в нашия случай, за да изведе, да кажем Y=h=5.

Изкуствен неврон и градиентно спускане

По-рано видяхме, че пресечната точка и наклонът на регресионна линия могат да бъдат директно изчислени с помощта на аналитична формула. Може ли изкуствен неврон, както току-що описахме, да намери тези стойности, без да използва никаква формула? Можем да използваме следната стратегия: можем да изберем произволни стойности за отсечка и наклон, да кажем W=(-1, 3), тогава невронът може да изчисли съответната регресионна линия и да я сравни с истински Y стойности. След това ще можем да изчислим разликата между изхода от неврона и истинското Y, т.е. загубата. В нашия случай средноквадратичната грешка е добра функция на загуба, която наричаме L. Бихме повторили процеса на избиране на произволни W стойности, докато загубата стане достатъчно малка или докато се уморим да опитваме. Тази стратегия може да работи добре за един неврон. Но ако имаме два или хиляди неврони, можем да прекараме цял живот в търсене. Ето защо тази стратегия звучи толкова налудничаво, че хората излязоха с по-добра идея, наречена градиентно спускане. Това е като да се спускаш по заснежени алпийски планини със ски свободен стил от върха през най-кратката пътека надолу към долината. Без да бъде убит.

Градиентно спускане е инструмент за намиране на стойностите за W, които минимизират функцията за загуба L, като разглеждат производната на тази функция по отношение на W . Да кажем, че сме избрали W=(-1, 3) и сме изчислили загубата за тези стойности, сега трябва да решим кои следващи стойности на W да опитаме за да имате намаляваща загуба. Идеята е да се изчисли производната на загубата, да кажем по отношение на прихващането, и да се проверят неговите знаци. Ако производната е положителна, това означава, че загубата се увеличава, така че трябва да опитаме с по-малък интервал. Ако производната е отрицателна, загубата намалява, така че можем да продължим да опитваме по-големи стойности на наклона. Ако производната е нула, ние сме достигнали минимум на загубата, надяваме се глобална. Можем да спрем и да разгледаме W като оптималното тегло, което минимизира загубата. Градиентното спускане изисква изчисляване на производни, което може да се превърне в кошмар, ако нямаме добър инструмент като Matlab. Благодарение на обратното разпространение ние дори не се нуждаем от такива инструменти, както ще видим по-късно.

Линейна регресия с Keras

Нека разгледаме практически как нашият неврон ще се справи със задачата за линейна регресия. Използваме Keras, библиотека на Python и добър спътник за експериментиране с дълбоко обучение. Ние създаваме модел с единичен неврон, скаларен вход, скаларен изход, афинна трансформация с тегло и отклонение и линеен изход. След това обучаваме нашия неврон върху точките от данни, докато използваме оптимизатора за стохастичен градиент на спускане. Функцията на загубите е средноквадратична грешка. Оптимизаторът ще извърши 5 итерации (епохи). За по-голяма простота ние не мащабираме данните.

Ето! Един единствен неврон успя да предскаже почти същата регресионна линия (зелено), която преди това изчислихме аналитично (оранжево). Прогнозираните стойности за наклона и отсечката са много близки, както е показано на изображението по-горе. Резултатите R2, мярка за годност, също изглеждат подобни и в двата случая. Изглежда, че изкуствената невронна мрежа наистина работи! Ами ако го направим малко по-трудно?

Нелинейна регресия с неврони

Нашият фермер скоро осъзна, че само малко неща в живота са линейни. Тенденцията при реколтата вероятно ще достигне плато и ще претърпи спад. По-долу визуализираме нов набор от данни, който показва така наречената тенденция на „една гърбица“.

Модел с три неврона

Очевидно единичен неврон с линейно активиране няма да може да улови поведението в тези нови данни. Първата мисъл е да промените функцията за линейно активиране и вместо това да използвате функция, подобна на S. Сигмоидната функция е добър кандидат, който се използва доста често в дълбокото обучение. Сигмоида би уловила перфектно нарастващата тенденция, наблюдавана в нашите данни. Намаляващата тенденция може да бъде уловена и от огледална сигма. Така имаме нужда от две сигмоиди, следователно два неврона и трети неврон, който ще обобщи и двете сигмоиди. Съответната архитектура е показана на изображението по-долу.

Първият неврон ще приеме скаларен X като вход, след което ще приложи афинна трансформация, използвайки тегло W1и отклонение. Резултатът ще премине през сигмоидно активиране, за да се получи h1. Нещо подобно ще се случи във втория неврон, за да произведе h2. Сега и двете числа h1 и h2 ще бъдат подавани в третия неврон, който ще извърши афинна трансформация чрез прилагане на теглата W31към h1и W32към h2, накрая добавяйки отклонение. Полученото q ще премине през линейно активиране, за да се получи формата на една гърбица.

Преминаване напред с изкуствени невронни мрежи

Нека изградим тази мрежа в Python, от нулата, без Keras. Мрежата има общо 7 тегла (и пристрастия), както видяхме в предишния раздел. Даваме стойности на 7-те тегла ръчно, извършваме прехвърляне напред, като използваме данните за функцията hump и начертаваме изхода от мрежата в същата графика като истинските стойности Y. Регулираме теглата ръчно, докато графиките съвпадат възможно най-близо. Правейки това, ние симулираме така нареченото предаване напред, което се извършва от Keras при обучение на мрежа.

Нелинейна регресия с Keras

Подобно на Касандра от Троя, ние успяхме да отгатнем перфектните стойности за W, така че изходът на мрежата превишаваперфектно данните. Въпреки че повечето специалисти по данни могат да направят такава магия, не всички хора имат тази дарба. За щастие има друг начин да направите това, за обикновените хора. Това е да използваме библиотека, като Keras, за да стартираме оптимизатор за градиентно спускане, който прави всичко възможно да намери тези 7 тегла за нас. Това е, което илюстрираме в кода по-долу.

След 50 000 епохи на обучение мрежата постига 96,69% ​​R2 резултат. Графиката по-горе показва неговата прогноза в сравнение с тази, която преди това получихме чрез ръчна настройка на теглата. Изглежда доста невероятно, нали? Като се имат предвид 3 неврона, точки за данни X и Y, мрежата може да се самонастрои фино, за да пасне на данните. Той е научил формата на данните без допълнително вникване. По-долу можем визуално да видим как търсенето на най-доброто W се е сближило към най-ниската загуба. Ако оставим оптимизатора да работи за допълнителни епохи, в крайна сметка ще достигнем 100% съответствие. Някои читатели на тази статия вече скърцат със зъби и мислят за прекомерно оборудване и мащабиране. Е, нека бъдем щастливи засега и да се върнем към тази гореща тема по-късно.

Този резултат е още едно доказателство в подкрепа на твърдението, че изкуствените невронни мрежи имат способността да улавят нелинейни зависимости в данните. Ето защо дълбокото обучение работи? Е, тук изневерихме малко. Проектирахме мрежата въз основа на нашите предварителни познания за двойната сигмоидална форма на данните и следователно, като избрахме сигмоида като функция за активиране. Данните от реален сценарий не винаги имат толкова ясна форма и в крайна сметка ще се заиграем, за да намерим правилната мрежова архитектура. Рано или късно ние ще въведем нашия възглед за света в мрежовата архитектура, превръщайки го в предубеден модел. Можете да разгледате другата ми статия за „отговорна наука за данни“. Засега нека приемем, че всички сме добри момчета. Въпросът защо дълбокото обучение работи обаче остава открит.

Логистична регресия с Keras

Нашият фермер не беше много доволен от модела на гърбицата, особено от втората му част, като му каза да очаква намаляване на реколтата. Искаше по-скоро да знае кои години да очаква добра реколта. По-долу създаваме набор от данни, който отразява ситуацията. Годините под 0 се класифицират като години с лоша реколта, докато годините след 0 предлагат добра реколта.

Нека сега да видим дали един прост неврон може да класифицира дадена година като добра година за прибиране на реколтата или не. Това е проблем с логистична регресия. По-долу подаваме нашите данни в модел на Keras, използвайки стохастичен градиентен низход като оптимизатор за загуба на двоична крос-ентропия (твърде много ключови думи, за да ви удивят). Постигаме 81% точност на класификацията, както можете да видите на диаграмата по-долу, функцията за сигмоидно активиране свърши добра работа.

Градиентно спускане в логистичната регресия

Проблемът с класификацията, който току-що решихме, е добър пример за навлизане в тъмния свят на градиентно спускане и обратно разпространение. Спомняме си, че в нашия неврон по-горе входът премина през афинна трансформация и резултатът беше въведен в сигмоидно активиране. Следователно резултатът е стойност между 0 или 1, вероятността за добра реколта. По-долу виждаме израза на този изход P(Y=1). Обърнете внимание, че афинната трансформация на X зависи от два параметъраβ0 и β1.

По време на обучение, за всеки вход Xi, невронът е в състояние да изчисли вероятността Pi и да я сравни с истинската стойност Yi. Грешката обикновено се изчислява с помощта на двоична крос-ентропия. Върши същата работа като средната квадратна грешка, която въведохме преди. Двоичната кръстосана ентропия измерва колко далеч от истинската стойност Yi (която е 0 или 1) е прогнозата Pi. Формулата, използвана за изчисляване на тази двоична кръстосана ентропияLi, е дадена по-долу.

Както можете да видите, загубата зависи от теглата β0 и β1. След като оптимизаторът за градиентно спускане е избрал произволни тегла, той избира произволно Xi, след което прави преминаване напред, за да изчисли загубата. Оптимизаторът повтаря това изчисление за всички входни точки от данни, ако използваме основния градиентен низход, или само за малки партиди от данни, ако използваме стохастичната версия. Пълната загуба се получава чрез сумиране на всички индивидуални загуби. След като оптимизаторът изчисли загубата, той ще изчисли нейната производна по отношение на теглата. Въз основа на знака на производната, той ще актуализира теглото положително или отрицателно.

Знаем, че искаме да вървим в обратна посока на производната и знаем, че искаме да направим стъпка, пропорционална на производната. Коефициентът на обучение λ е това, което контролира тази пропорция за всяко тегло W (β0 или β1).

Обратно разпространение в логистична регресия

Както можете да видите на изображението по-горе, актуализирането на теглата изисква изчисляване на частичните производни на загубата по отношение на всяко тегло. Как да направим това? Е, можем да използваме математиката в гимназията, за да направим това. В изображението по-долу се опитваме да изчислим извеждането на функцията за загуба на кръстосана ентропия по отношение на β0 и β1.

За мрежа с един неврон това е чудесно решение. Но представете си мрежа със стотици неврони, каквито обикновено срещаме при дълбокото обучение. Обзалагам се, че не искате да изчислявате получената производна. Дори и да успеете в това, ще трябва да актуализирате формулите си всеки път, когато архитектурата на мрежата се промени, дори само малко. Тук влиза в действиеобратното разпространение. Алгоритъмът за обратно разпространение първоначално е въведен през 70-те години на миналия век, но значението му не е оценено напълно до доклад от 1986 г. на Джефри Хинтън.

Обратното разпространение използва верижното правило, което е удобна мнемоника за писане на производни на вложени функции. Например, ако имаме мрежа с един неврон, който се захранва във втори и накрая в трети, за да получи изход. Функцията на обща загуба f е функция на функцията на загуба g на първите два неврона, по подобен начин g е функция на функцията на загуба hна първия неврон.

По принцип, докато вървим напред от входовете, изчислявайки изходите на всеки неврон до последния неврон, ние вече оценяваме и малки компоненти на производното. В примера по-горе можем да изчислим dh/dx вече, когато преминаваме напред през първия неврон. След това можем да изчислим dg/dh, когато преминаваме напред през втория неврон. Накрая започваме да изчисляваме df/dg, минавайки назад през невроните и като използваме повторно всички вече изчислени елементи. Това е произходът на обратното разпространение на името. Има няколко изпълнения и вкусове на тази техника. В името на простотата, ние го поддържаме просто тук.

За да илюстрираме как работят верижното правило и обратното разпространение, нека се върнем към функцията за загуба за нашата 1-невронна мрежа със сигмоидно активиране. Функцията на загубата беше определена като двоична кръстосана ентропия, която може да бъде разделена на две части A и B, както е показано по-долу.

Нека разгледаме по-отблизо част А от функцията на загубата. Той може да бъде разделен на блокове, подчертани с червени кутии на изображението по-долу.

Обратното разпространение изисква да се изчисли производната на тази функция във всяка дадена точка от данни X за всяко дадено тегло W. Това се прави чрез изчисляване на производната на всеки блок и събиране на всички заедно с помощта на верижното правило. По-долу виждаме как това ще работи за X=3 и W=3.

Всичко, от което се нуждаем, е да можем да изчисляваме производни на малките блокове (наречени по-горе променливи). Такива блокове са известни, защото функциите за активиране обикновено са известни. Те могат да бъдат сигмоидни, линейни, ReLu и т.н. Това са диференцируеми функции с известни производни. Можете да намерите пълния списък с модерни функции за активиране тук. Следователно изчисленията по-горе могат да бъдат изградени по време на изпълнение с помощта на изчислителна графика. Keras може да разгледа вашата мрежова архитектура и функциите за активиране, използвани във всеки неврон, за да изгради изчислителна графика по време на компилация на модела. Тази графика се използва по време на обучение за извършване на предаване напред и обратно разпространение. По-долу е представен пример за изчислителна графика за функцията на загуба на кръстосана ентропия.

Групиране с неврони

Разбирането как работят градиентното спускане и обратното разпространение е чудесна стъпка към разбирането защо дълбокото обучение всъщност работи. Е, все още не сме навлезли толкова дълбоко. Досега използвахме само 3 неврона. Нашият фермер може да твърди, че връзката между годините и количеството на реколтата е твърде сложна, за да бъде представена само от два класа: добри или лоши. В този раздел ще изследваме проблем с групиране с изкуствена невронна мрежа. Нека симулираме някакъв облак от данни, разпределени в три групи, представящи качеството на прибиране на реколтата. Разглеждаме три точки в равнина (x,y) с координати (-2,0), (0,1.7) и (2.1,0). Около всеки от тези три центъра създаваме облак от 100 произволно генерирани точки. За радиалното разстояние на всяка една от тези точки от нейния център използваме произволно нормално разпределение. За ъгловата координата на всяка една от точките на „облака“ използваме равномерното разпределение.

Сега ще създадем двуслойна изкуствена невронна мрежа, която може да предвиди дали произволно генерирана точка в равнината принадлежи на облак 0, 1 или 2. Входният слой има 50 неврона (задълбочаваме се)! Получава две стойности (x, y). Функция за активиране на ReLU се прилага към афинната трансформация на входа. Резултатът се подава в изходен слой с 3 неврона, които използват функцията за активиране на softmax, за да предвидят един от трите класа облак. Оптимизаторът на стохастичния градиент се използва за решаване на проблема с класификацията за оценка на 303 тегла и отклонения чрез минимизиране на категориалната кръстосана ентропия, използвана като функция на загуба. Разделяме данните на 50 точки от данни за обучение на класификатора и 50 за валидиране. Ние тренираме в партида от 5 точки през 20 епохи. След обучение извършваме и прогнозиране на тестови набори. Използваме argmax, за да преобразуваме прогнозирания категориален вектор в оригинални етикети преди показване.

Както е показано по-горе, невронната мрежа върши добра работа при разделянето на класовете в тестовия набор (десен график). На някои извънредни стойности, открити в оригиналните данни (вляво), се присвоява различен етикет от мрежата (вдясно), за да се създадат ясни граници. Ние постигаме 95,33% точност на класификацията на данните от теста.

По-долу произволно генерираме чисто нови и невиждани координати в самолета. След това използваме обучената мрежа, за да предвидим класа (облак). Както можем да видим на графиката, мрежата ясно разделя и трите облака, въпреки че има няколко точки много близо до границите, които са добри кандидати за фалшиво положително/отрицателно. Като цяло изглежда, че започваме да правим задълбочено обучение.

Сега въодушевихме внука на внука на нашия фермер от дълбокото обучение! Насочете се направо към http://playground.tensorflow.org, за да изградите своя собствена изкуствена невронна мрежа чрез визуално бърникане на слоеве, неврони, функция за активиране, обучение и тестване направо във вашия браузър. Когато приключите, върнете се тук за още вълнуващи неща.

Autoencoder за обезшумяване на изображения

Читателите, които досега не са били впечатлени, вече знаят защо дълбокото обучение работи. За останалите от нас сега ще разгледаме пример за мрежова архитектура, която става доста задълбочена. Autoencoder е направен от двойка от две свързани мрежи: модел на енкодер и модел на декодер. Целта на автокодера е да намери начин да кодира входа в компресирана форма (латентно пространство) по такъв начин, че декодираната версия да е възможно най-близо до входа. Моделът на кодерпревръща входа в малко плътно представяне. Моделът декодерможе да се разглежда като генеративен модел, който е в състояние да генерира специфични функции. И енкодерът, и декодерът обикновено се обучават като едно цяло. Функцията за загуба наказва мрежата за създаване на изход, който се различава от входа. Следователно енкодерът се научава да запазва колкото се може повече от съответната информация, необходима за ограничаване на латентното пространство, и умело да отхвърля неподходящи части, напр. шум. Декодерът се научава да приема компресираната латентна информация и да я реконструира в пълен вход без грешки. Автокодерът може да бъде полезен за намаляване на размерността и обезшумяване на изображения, но може да бъде успешен и при неконтролиран машинен превод (уау!).

По-долу дефинираме най-простата архитектура на автоенкодер, който обработва изображения на шумни ръкописни цифри. Ние предоставяме на мрежата оригинални изображения x, както и тяхната шумна версия x~. Мрежата се опитва да реконструира своя изход x’, за да бъде възможно най-близо до оригиналното изображение. Правейки това, той се научава как да обезшумява всяка ръкописна цифра.

В следващите няколко параграфа виждаме как би работила такава мрежа чрез прилагане на нейна малка версия с помощта на Keras.

Вход: изображение в мащаб на сивото 28x28. Следователно входът е вектор от 784 елемента.

Кодер: единичен плътен слой с 64 неврона. Следователно латентното пространство ще има измерение 64. Използваната функция за активиране е ректифицирани единици (ReLu), избрани от най-добрите практики. Функцията за активиране е прикрепена към всеки неврон в слоя и определя дали трябва да бъде активиран („задействан“) или не, въз основа на това дали входът на всеки неврон е от значение за прогнозата на автокодера. Функцията за активиране също помага за нормализиране на изхода на всеки неврон до диапазон между 1 и 0.

Декодер: единичен плътен слой със 784 неврона, съответстващ на 28x28 изображение в сива скала. Функцията за активиране на сигмоида се използва като най-добра практика за задачата за класификация (вход към енкодер срещу изход от декодер).

Оптимизатор: използваме двоична крос-ентропия като функция на загубата и Adadelta като оптимизатор за минимизиране на функцията на загубата.

Данни: използваме цифри MNIST за генериране на синтетични цифри с шум чрез прилагане на матрица на шума на Гаус и изрязване на изображенията между 0 и 1. По-долу показваме някои от цифрите с шум.

Все още можем да разпознаем цифри, но едва. Затова искаме да използваме нашия автоматичен енкодер, за да се научим да възстановяваме оригиналните цифри. Ние правим това, като монтираме автокодера за 100 епохи, докато използваме шумните цифри като вход и оригиналните обезшумени цифри като цел. Така автокодерът ще минимизира разликата между шумни и чисти изображения. Правейки това, той ще се научи как да премахва шума от всяка невидима ръкописна цифра, която е била произведена с подобен шум.

По-долу начертаваме входни изображения с шум срещу тяхната изчистена версия.

  • като цяло шумът се премахва много добре. Белите точки, въведени изкуствено върху входните изображения, са изчезнали от почистените изображения. Цифрите могат да бъдат разпознати визуално. Например шумната цифра „4“ изобщо не беше четлива, сега можем да прочетем нейната изчистена версия.
  • обезшумяването има отрицателна страна върху качеството на информацията. Реконструираните цифри са някак замъглени. Декодерът е добавил някои функции, които не присъстваха в оригиналното изображение, напр. 8-та и 9-та цифра по-долу са едва разпознаваеми.

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

Конволюционни невронни мрежи

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

Сега нека изградим дълбока мрежа. Започваме с първи конволюционен слой Conv2D, който има 16 филтъра, всеки с размери 3x3. Подплатата е същата, стъпката е 1, следователно картата на изходните характеристики ще има форма 28x28x16. Ние прилагаме функция за активиране на ReLu към този изход, след като добавим отклонение към него. Конволюцията причинява повторение на информация, идваща от съседни области на изображението, което води до голяма размерност. Обединяванетовзема област от изхода на конволюционния слой и връща обобщена стойност: обикновено максимална, но може да се използва средна, минимална или всякаква функция.

Добавяме слой MaxPooling2D с размер 2x2, крачка 1 и същата подложка. Това означава, че ще вземем максималната стойност от 2x2 парчета и ще преминем с 1 стъпка към следващото парче. Изходът от групирането ще бъде подплатен с нули, за да има същото измерение като входа. Обединяването винаги се извършва след прилагане на функцията за активиране към конволюцията.

CNN работят най-добре, когато се вземат предвид множество мащаби. Затова дублираме още веднъж слоевете за навиване и за максимално обединяване. Полученият енкодер извежда представяне на изображението във формата 7x7x32. Това е така, защото входното изображение 28x28x1 се свива от всеки от 32-те 3x3 филтъра в първия слой Conv2D, връщайки пространство на характеристиките с размери 28x28x32. MaxPooling намалява това представяне до половината 14x14x32. Вторият слой Conv2D обгръща всяко от представянето 14x14x32, използвайки набор от 32 филтъра 3x3. Това води до пространство за функции с размери 14x14x32. Последният слой MaxPooling намалява представянето с половин размер, което води до формата 7x7x32.

Декодерът има същата архитектура като енкодера със слоеве, подредени в обратен ред. Използваме слой UpSampling, за да възстановим намаляването на размерността, извършено от MaxPooling в енкодера. Накрая добавяме конволюционен слой, който възстановява броя на каналите в последното представяне до 1. Функцията за активиране на Sigmoid се използва за решаване на проблем с класификацията, където двоичният резултат отразява колко подобно е декодираното изображение в сравнение с входното. Можем да наблюдаваме как декодиращата част на автокодера е възстановила оригиналната форма на изображението (28x28x1).

Пълната мрежа има 28 353 тежести и пристрастия за трениране. Използваме двоична кръстосана ентропия като функция на загуба и Adadelta като оптимизатор за минимизиране на функцията на загуба. След 20 епохи автоматичният енкодер на CNN има стойност на загуба на влак/тест от около 0,098, в сравнение с по-високата загуба от 0,1235, която имахме с плътния автоенкодер. Нашият автоматичен енкодер със CNN се справя доста добре с невидяни изображения. В сравнение с простия автоматичен енкодер с 1 плътен скрит слой от предишния раздел, обезшумените изображения изглеждат много по-добре.

По-дълбоко

Начинът за подреждане на конволюционни слоеве е повече изкуство, отколкото наука. Не се страхувайте да погледнете мрежата VGG по-долу, тя беше предложена през 2014 г. за класифициране на 14 милиона изображения в до 1000 класа с 92,7% точност на теста. Той беше обучен в продължение на 2 седмици, за да изчисли своите 14 714 688 тегла. Ужасен! Има още такива свръхмасивни мрежи: GoogLeNet, ResNet, DenseNet, MobileNet, Xception, ResNeXt, само за да назовем няколко.

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

Заключение

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

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

Покриването на Deep Learning в една статия е шега, ние не сме се опитвали да направим. Класическите книги „Задълбочено обучение“от Иън Гудфелоуи „Задълбочено обучение с Python“от Франсоа Шолеса отлични отправни точки.

Защо задълбоченото обучение работи? Това е въпрос с отворен край. Благодаря на Бога.

Благодаря ви, че прочетохте. Погледнете статията ми за байесовия подход в машинното обучение по-долу.