Сети развития (DN): новая машина Тьюринга

алгоритм

Если ее необходимо разделить, то работу профессора Венга можно разделить на два периода: 1) CCIPCA+IHDR, 2) CCILCA+DN. IHDR, как попытка реализовать роботизированный мозг, явно провалилась. Потому что нет большой корреляции между работой двух периодов до и после [Тем не менее, IHDR по-прежнему является отличной моделью дополнительного обучения, и ее стоит изучить и понять глубже.]. Почему IHDR не может служить окончательной моделью развития (мозга) для роботов? Ответ профессора Венга таков: человеческий мозг не имеет центрального контроллера, в то время как IHDR имеет центральный контроллер для регулирования всех процессов обучения [IHDR — это глобальная модель обучения, DN — это локальная модель обучения ::: МОЖЕТ БЫТЬ]. В сочетании с контекстом это означает, что сеть развития (DN) не имеет центрального регулирования. Эта статья представляет DN на основе лекций профессора Венга и связанных с ним статей. Сначала систематически вводится идея сети развития, а затем вводится метод Затем для дальнейшего понимания сети развития используется пример реализации сети развития Где-что-сеть Наконец, экспериментальные результаты и полный текст анализируется и обобщается. Пример программы Python в этой статье был загружен на github.

@[toc]

1. Мозг

1.1 Контекст от двигателя

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

  1. Когда новорожденную кошку поместили в среду только с вертикальными границами на некоторое время, а затем поместили в нормальную среду, мы обнаружили, что нейроны в ее области V1 не реагировали на горизонтальные границы (а именно: она не смотрела на горизонтальный край). 【Блейкмор и Купер, Природа 1970】

在这里插入图片描述2. На изображении ниже показано, как на клетки зрительного нерва в левой зрительной коре преобладает информация, поступающая от правого или левого глаза. Нормальная ситуация показана на левом изображении ниже. Условно говоря, в большинстве нейронов левой зрительной коры преобладает вход правого глаза, а в значительной части преобладает левый глаз. Теперь закройте правый глаз 10-дневного котенка через 21 день (то есть на 31-й день после рождения), ситуация будет такой, как показано на среднем рисунке. Доминирование правого глаза уменьшилось. Еще через 6 дней результаты показаны справа. В основном доминирует левый глаз. [Примечание: в нормальных условиях левый глаз воспринимает правое полушарие, а правый глаз — левое полушарие]

在这里插入图片描述3. Отрежьте зрительный нерв Через некоторое время обнаруживается, что зрительный нерв автоматически соединяется с нейронами в слуховой области. То есть слуховая область используется для того, чтобы «видеть». [Сур, Ангелуччи и Шарм, Природа, 1999 г.]

在这里插入图片描述

1.2 Мозг — это не каскад

Глубокое обучение использует глубокую нейронную сеть в качестве модели обучения, которая представляет собой каскадную структуру. Однако мозг не является каскадной структурой, и синаптические связи между отдельными нейронами запутанно связаны.在这里插入图片描述

1.3 Унификация символов и объединений

Мозг использует взаимосвязь нейронов для реализации обучения и хранения знаний, а также обладает способностью к логическому мышлению. Это показывает, что мозг представляет собой единство символизма и коннекционизма.在这里插入图片描述

1.4 Автономное развитие

Люди развиваются от оплодотворенной яйцеклетки до ребенка и от ребенка до взрослого человека, этот процесс является автономным развитием. Естественная идея состоит в том, что если у робота есть тело и автономная программа развития, то он будет развиваться посредством автономного взаимодействия с окружающей средой и другими агентами, как и люди, и постепенно приобретать все больше и больше знаний, а также становиться умнее. Это также основная движущая цель исследования профессора Венга по теории развития автономного разума.在这里插入图片描述

2. Новые универсальные машины Тьюринга

2.1 Конечные автоматы (FA)

Конечные автоматы или машины, называемые конечными состояниями. Сначала мы рассмотрим конечный автомат (FSM), который очень похож на FA. Конечный автомат (FSM) состоит из конечного числа состояний и отношений перехода состояний. Конечный автомат, показанный на рисунке ниже, состоит из 6 состояний, и условия перехода между состояниями также четко даны на рисунке. Например, если текущее состояние равно 2, и в это время вводится символ I, он перейдет в состояние 6.在这里插入图片描述Однако конечный автомат состоит из конечного набора внутренних состояний и набора правил управления, которые определяют, в какое состояние он должен перейти после чтения входного символа в текущем состоянии.

[Управление машиной Тьюринга является конечным автоматом]

2.2 Машина Тьюринга

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

在这里插入图片描述Люди также могут быть абстрагированы в машины Тьюринга. Всех, кто может принимать решения и думать, можно абстрактно рассматривать как машину Тьюринга, и у каждого есть своя операционная система. Набор входных состояний — это вся информация, которую вы можете увидеть, услышать, понюхать и ощутить в своем окружении, а возможный набор выходных данных — это ваши слова и действия, а также выражения, которые вы можете выразить. Коллекции внутренних состояний намного сложнее. Поскольку мы можем думать о любой комбинации состояний нервной клетки как о внутреннем состоянии, то все возможные комбинации состояний нервных клеток будут астрономическими. Это человеческая память.Пока у машины Тьюринга есть внутреннее состояние, у нее есть память. 在这里插入图片描述

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

2.3 Универсальная машина Тьюринга

Мы можем закодировать машину Тьюринга, представленную выше, как строку . Далее мы можем построить специальную машину Тьюринга, которая принимает код любой машины Тьюринга M в качестве входных данных [машина Тьюринга принимает данные в качестве входных данных, общая машина Тьюринга принимает в качестве входных данных машину Тьюринга], а затем моделирует работу M, например что машины Тьюринга называются универсальными машинами Тьюринга. Современный электронный компьютер фактически представляет собой симуляцию такой универсальной машины Тьюринга, которая может принимать программу, описывающую другие машины Тьюринга, и запускать программу для реализации описанного программой алгоритма.

在这里插入图片描述

2.4 Возникновение UTM

在这里插入图片描述На приведенном выше рисунке показан традиционный конечный автомат, который можно представить в виде символьной таблицы поиска с тем же значением, что и ниже:在这里插入图片描述Далее кодируем: А-00;Б-01;С-10;Д-11. Доступна следующая таблица поиска. Таблица поиска — это эмерджентный конечный автомат.

在这里插入图片描述Мы принимаем Z как состояние и X как вход. В начальном состоянии 00, когда на входе 01, он достигнет следующего состояния 01, а затем, когда будет введено 10, он перейдет в состояние 10, продолжит ввод 10, он перейдет в выключенное состояние 10, в на этот раз введите 11, он перейдет в состояние 11. Это очень близко к главному герою этой статьи [Development Network (DN)].在这里插入图片描述

3. Сеть развития

3.1 От зарождающейся UTM к развивающейся сети

Также следите за таблицей поиска и примерами преобразования выше. Мы рассматриваем состояние Z как ввод человеческого восприятия, а ввод X — как движение мышц человека. Мы связываем X и Z как узел в карте памяти (сеть развития). Y неявно присутствует в самой модели человека или робота, и его не нужно изучать.

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

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

[Примечания: чтобы лучше понять взаимосвязь между возникающей машиной Тьюринга и сетью развития, здесь упрощен процесс обучения и использования сети развития. Процесс обучения реальной сети развития учитывает сходство между информацией, которая эффективный①Процесс кластеризации: Анализ состава листа (LCA) и в соответствии с②Правила Хеббадля обновления параметров сети. 】

Яркий пример показан на следующем рисунке: [Ключом к пониманию сетей развития является то, что правила управления машинами Тьюринга неявно заложены в онтологии человека и робота и не нуждаются в изучении. Люди и роботы сами по себе являются моделью, выполнение определенных действий, естественно, явно повлияет на окружающую среду]在这里插入图片描述

3.2 Характеристики сетей развития

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

  1. Заземление: Восприятие физического мира и воздействие на него;
  2. Emergent: внутреннее представление генерируется автоматически;
  3. Естественно: это естественное кодирование, а не ручное кодирование;
  4. Инкрементальный: не пакетное обучение, не набор данных;
  5. Корпус черепа: люди не могут изменять внутричерепные параметры;
  6. Примечание. У него есть механизм внимания для перцептивных и моторных функций;
  7. Мотивируется: избеганием боли, поиском Куайдонга, любопытством и т. д.;
  8. Абстрактно: умеет извлекать понятия и правила из контекста;

Под сомнением еще одно:Сети развития объединяют контролируемое и неконтролируемое обучение.

3.3 Автономные процедуры развития

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

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

[Примечание: Следовательно, необходимо представить процесс обучения нейрона только для понимания обучения всей сети развития, независимо от того, насколько сложна сеть развития. Ответ каждой нейронной клетки развивающейся сети состоит из трех частей: а) восходящий (вход от предыдущего слоя к текущему слою) ответyy;b) ответ сверху вниз (ввод со следующего уровня на текущий уровень)aa;c) Тормозные ответы других нейронов того же слояhh. Общий ответz=g(wby+wpawhh)z=g(w_b y+w_p a -w_h h)gg— произвольная функция активации. Зеленый кружок и толстая линия на рисунке ниже представляют полную нейронную ячейку. линия, соединенная с толстой линией, — это нисходящий вход, а соединенные пунктирные линии — тормозные входы интернейронов того же слоя. 】

在这里插入图片描述

  1. Боковое торможение: В биологических нейронных сетях, таких как сетчатка глаза человека, существует явление «латерального торможения», то есть после возбуждения нервной клетки ее ответвления будут тормозить другие окружающие нервные клетки.Латеральное торможение — это механизм, с помощью которого нейроны одного и того же слоя конкурируют друг с другом.. Чтобы сделать латеральное торможение более эффективным в развивающихся сетях: а) сильно реагирующие нейроны могут эффективно тормозить слабо реагирующие нейроны; б) слабо реагирующие нейроны не влияют на сильно реагирующие нейроны. Профессор Венг использует правило конкуренции топ-к, то есть нейроны в одном слое сортируются от сильных к слабым, топ-к нейронов имеют ненулевое обновление веса, а веса других нейронов не меняются.

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

  1. Хеббианское обучение: Теория Хебба описывает основной принцип синаптической пластичности, то есть непрерывная и повторяющаяся стимуляция пресинаптических нейронов постсинаптических нейронов может привести к увеличению эффективности синаптической передачи. Эта теория была предложена Дональдом Хеббом в 1949 году и известна также как закон Хебба. Теорию Хебба можно использовать для запуска «ассоциативного обучения», при котором сила синапсов между нейронами увеличивается из-за повторной стимуляции нейронов. Такой метод обучения называется обучением по Хеббу. Теория Хебба также стала биологической основой обучения без учителя.

[Примечание: предположим, что вес нейрона текущей победы в соревновании равенvjt1v_j^{t-1}, текущий входy(t)y(t), нейрон победы обновляется по следующей формуле:

v_j^{t}=\alpha v_j^{t-1}+(1-\alpha) y(t) \tag{1}в,1α1-\alphaскорость обучения,α\alphaскорость забывания. 】

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

在这里插入图片描述

[Примечание: листовой ингредиент состоит изАлгоритм анализа компонентов листа | Подробный вывод и применение см. В этом блогеВ результате анализ листовых компонентов представляет собой алгоритм кластеризации, и каждый центр кластера представлен вектором направления в его направлении. Чтобы было понятнее, расстояние в этом алгоритме кластеризации определяется двумя векторами.cos(θ)cos(\theta)сказал, из которыхθ\thetaпредставляет собой угол между двумя векторами. Мы знаем, что метод измерения расстояния имеет большое влияние на эффект алгоритма кластеризации, и определенное измерение расстояния может быть подходящим только для некоторых конкретных данных. Профессор Венг использует анализ листовых компонентов в качестве меры расстояния, и результаты неплохие. Основная причина заключается в том, что его входные данные - это данные изображения, и размерность очень высока. В таком многомерном входном пространстве данные в основном распределены. на гиперсфере, поэтому использование листовых ингредиентов уместно. Однако для некоторого низкоразмерного или разбросанного по всему пространству состояний распределения данных листовой компонент не подходит. Как показано на рисунке ниже, это двумерный набор данных, и мы не можем сгруппировать его в соответствующие классы, используя анализ конечных компонентов. 】

在这里插入图片描述

резюме: Основные функции автономной развивающей программы приведены выше, и каждая функция подробно объяснена. Латеральное торможение, хеббовское научение и листовые компоненты не являются полностью самостоятельными личностями, это взаимозависимые отношения между вами и мной, и вами во мне. Процедуру развития отдельной нейронной клетки можно рассматривать как анализ листовых компонентов, однако алгоритм анализа листовых компонентов обновляется правилом Хебба и вектором центра кластера (параметр веса нейрона) победы латерального торможения. Это автономный алгоритм, и эксперименты также подтвердили его эффективность. Есть две основные причины, по которым я отношусь к этому алгоритму: 1) Разумно ли забывать? 2) Является ли кластеризация листовых компонентов общей для всех распределений данных? Относительно выбора группирующих мер расстояния есть поговорка: какой из них использовать, зависит от того, какой тип данных у нас есть и каково наше представление о сходстве.Конечно, я также пытаюсь интегрировать другие меры расстояния в автономные в процессе развития. программа. Однако текущая программа вегетативного развития сосредоточена на анализе листовых компонентов, то есть, если метрика расстояния изменена, необходимо заново разработать новую программу вегетативного развития. Это все еще довольно сложная задача.

3.4 Примеры сетей развития

Сети «где-что» (WWN)在这里插入图片描述

4. Пример DN: Где-какая-сеть

4.1 Подготовка данных

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

4.1.1 Описание процесса строительства

Во-первых, мы расскажем, как построить данные, необходимые для обучения сети «где-что». Мы можем сфотографировать сцену, а затем пометить ее местоположением и типом. Однако этот процесс очень трудоемок. Основная цель этого раздела — дать наглядное представление о разрабатываемых сетях с последующим описанием реальных приложений. Поэтому в этом разделе используются искусственно созданные данные для обучения DN. Искусственно созданные данные изображения могут автоматически получать метки типа и местоположения объектов, избавляя от необходимости маркировки вручную. Ниже приведен простой метод искусственного построения обучающих данных.在这里插入图片描述

  • Фоновое изображение: чтобы имитировать реальное изображение сцены, объект обычно имеет фон в качестве подложки. Например, кот на диване, диван — это фон кота. Размер фона этой части составляет 19x19, который создается случайным вырезанием небольших блоков 19x19 на 13 реальных изображениях сцены в левой части рисунка выше.
  • Изображения объектов: в этом разделе в качестве объектов используются изображения пяти животных с низким разрешением 11x11. Это 1-кошка, 2-собака, 3-слон, 4-свинья, 5-грузовик.
  • Ввод: случайным образом выберите изображение объекта и поместите его в случайную позицию случайно выбранного фонового изображения (здесь есть 25 дополнительных позиций, а синяя сетка на среднем изображении выше — это необязательное центральное положение изображения объекта). (как показано в середине рисунка выше)
  • Где-какие двигатели: где двигатель и какой двигатель занимают положение и тип во время строительства в качестве входных данных.

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

4.1.2 Конструктор образцов

  • 1. Произвольно обрежьте реальную картинку, чтобы получить фоновое изображение 19x19.
def get_background(background_height, background_width):
    epsilon_error = 1.0/(256*sqrt(12))
    f = open('backgrounds/backgrounds_to_use.txt')
    splitData = f.read().split("\n")
    curr_num = np.random.randint(len(splitData) - 2) + 1
    img_file = 'backgrounds/'+splitData[curr_num]+'.'+splitData[0]
    curr_img = np.array(Image.open(img_file))
    rows, cols = curr_img.shape
    ul_row = np.random.randint(rows-background_height)
    ul_col = np.random.randint(cols-background_width)
    bg = curr_img[ul_row:ul_row + background_height, ul_col:ul_col + background_width]
    bg1 = copy.deepcopy(bg)
    samplemin = np.min(bg1)
    samplemax = np.max(bg1)
    bg = (bg - samplemin)/(samplemax-samplemin+epsilon_error)
    plt.imshow(bg)
    plt.show()
    ul_img = Image.fromarray(np.uint8(bg))
    ul_img.show()
    return bg
  • 2. Случайным образом выберите объект в качестве изображения переднего плана и добавьте его к фоновому изображению.
def add_foreground(background, training_type):  # 01:cat; 02:dog; 03:elephant; 04:pig; 05:truck
    f = open('foregrounds/foregrounds_to_use.txt')
    splitData = f.read().split("\n")
    curr_num = np.random.randint(training_type) + 1
    img_type = curr_num - 1
    img_file = 'foregrounds/'+splitData[curr_num]+'.'+splitData[0] 
    curr_img = Image.open(img_file, 'r')
    fg = np.array(curr_img.convert('L'))
    obj_width, obj_height = fg.shape
    fg1 = copy.deepcopy(fg)
    samplemin = np.min(fg1)
    samplemax = np.max(fg1)
    fg = (fg - samplemin)/(samplemax-samplemin)
#     plt.imshow(fg)
#     plt.show()
    p_r = np.random.randint(5)
    p_c = np.random.randint(5)
    r = (p_r)*2
    c = (p_c)*2
    position = p_r*5+p_c
    background[r:r+obj_width, c:c+obj_width] = fg
#     plt.imshow(background)
#     plt.show()
    return background, img_type, position
  • 3. Используя построенное входное изображение, далее получить, где и какие моторы, и инкапсулировать его в стандартный формат выборочных данных .
def get_image(input_dim, z_neuron_num):
    """
    1: cat; 2:dot; 3:elephant; 4:pig; 5:truck
    position: (row-1)*col
    """
    epsilon_error = 1/(256*sqrt(12))
    background_width = input_dim[0]
    background_height = input_dim[1]
    
    bg = get_background(background_height, background_height)
    
    
    training_type = 1
    if len(z_neuron_num) != 1:
        training_type = z_neuron_num[0]
    
    training_image, img_type, position = add_foreground(bg, training_type)
    true_z = []
    if len(z_neuron_num) != 1:
        true_z.append(img_type)
        true_z.append(position)
    else:
        true_z.append(position)
    true_z = np.array(true_z)
    return training_image, true_z

4.1.3 Пример конструкции

На картинке ниже показаны случайно выбранный фон, случайно выбранные объекты и случайно расположенные позиции для получения окончательного выходного изображения, а также где и какие моторы. [Примечание: поскольку изображение нормализовано и отображается с помощью plt.imshow из matplotlib, отображение отличается от реального изображения в градациях серого]在这里插入图片描述

4.2 Введение в сеть «где-что»

Простой пример сети «Где-Что», представленной в этой статье, показан на рисунке ниже [это должна быть самая простая форма, но хотя воробей маленький, но частей столько, сколько должно быть]. Сеть состоит из трех слоев ввода [Вход], основной части сети разработки [DN] и выхода [Двигатели]. Ядром является DN, отмеченный красным прямоугольником, в котором хранятся все полученные знания. И в этом демонстрационном примереКоличество сетевых нейронов в DN адаптивно увеличивается, количество нейронов в слое развития равно 25x(3^split_times), где split_times — это количество раз, когда необходимо выполнить разделение [Это немного похоже на митоз клеток.В отличие от клеток, которые можно разделить только на две части, здесь один узел может быть разделен на установленное нами значение, которое здесь равно 3.]. Количество нейронов во входном слое равно векторизованной длине входного изображения, 19x19=361. В каком двигателе 5 нейронов и в каком двигателе 25 нейронов. Количество нейронов во входном слое и моторном слое напрямую определяется образцом.在这里插入图片描述

4.3 Обучение сети «Где-что»

Первая характеристика DN заключается в том, чтоin-place. Так называемыйin-placeТо есть сеть локальна, обновление отдельного нейрона связано только с ним самим и окружающими нейронами, и обновление каждого нейрона использует один и тот же набор программ развития (подобно тому, как клетки человеческого тела используют один и тот же набор). ДНК). Поэтому нам нужно только объяснить параметры, расчет вывода и обновление веса нейрона в DN. Метод и шаги обновления одинаковы для всех нейронов.

4.3.1 Инициализация веса

Нейроны DN имеют в общей сложности пять параметров: ①bottom up weight;②top down weight;③lateral weight;④inhibit weight;⑤synapse factor. Объяснение первых трех параметров можно увидеть на рисунке ниже. Мы не рассматриваем последние два набора параметров в первую очередь, а используем только первые три параметра для расчета выходного сигнала нейрона, как показано на рисунке ниже [пожалуйста, внимательно прочитайте рисунок ниже]. Сначала вычислите реакцию X, реакцию Y, затем взвесьте сумму ответов двух, чтобы получить временную реакцию Temp Y, затем рассмотрите латеральный параметр, чтобы получить реакцию латерального нейрона на нейрон, и сравните ее. с суммированием Temp Y Weighted дает окончательный ответ нейрона Y.在这里插入图片描述Четвертый параметр:inhibit weightЭто параметр торможения того же слоя, то есть при активации нейрона в соответствующей пропорции будут активироваться только близлежащие нейроны, а остальные чуть удаленные нейроны будут тормозиться [для текущей выборки параметры не обновляются ]. Пятый параметр:synapse factorявляется фактором выбора внимания. Для разных нейронов важность различных размерностей входных данных не одинакова, поэтому для конкретного входа [X или Z] каждый нейрон в Y присоединяется с вектором факторов, равным единице размерности входного вектора. каждый элемент вектора фактора представляет важность соответствующего элемента входного вектора, и чем больше значение, тем он важнее. [Это немного похоже на выбор функции]

В этом примере четвертый параметр используется в функции соревнования top-k; пятый параметр используется только при выборе внимания Y на входе X, что позволяет сети развития адаптивно выбирать важные измерения перцептивных данных. .

Ниже приведены определения параметров сети и исходные функции в этом примере.

    def dn_create(self):
        self.y_lsn_flag = np.zeros((1, self.y_neuron_num))
        self.y_firing_age = np.zeros((1, self.y_neuron_num))
        self.y_inhibit_age = np.zeros((1, self.y_neuron_num))
        
        self.y_bottom_up_weight = np.ones((self.x_neuron_num, self.y_neuron_num))
        self.y_top_down_weight = []
        for i in range(self.z_area_num):
            self.y_top_down_weight.append(np.ones((self.z_neuron_num[i], self.y_neuron_num)))
        self.y_lateral_weight = np.zeros((self.y_neuron_num, self.y_neuron_num))
        self.y_inhibit_weight = np.ones((self.y_neuron_num, self.y_neuron_num))
        
        self.y_synapse_flag = 1
        """
        1: only bottom-up
        2: bottom-up + top-down
        3: bottom-up + top-down + lateral
        4: bottom-up + top-down + lateral + inhibit
        """
        self.y_synapse_coefficient = [0.8, 1.2, 5.0]
        self.y_synapse_age = 20
        
        self.y_bottom_up_synapse_diff = np.zeros(self.y_bottom_up_weight.shape)
        self.y_bottom_up_synapse_factor = np.ones(self.y_bottom_up_weight.shape)
        
        self.y_top_down_synapse_diff = []
        self.y_top_down_synapse_factor = []
        for i in range(self.z_area_num):
            self.y_top_down_synapse_diff.append(np.zeros(self.y_top_down_weight[i].shape))
            self.y_top_down_synapse_factor.append(np.ones(self.y_top_down_weight[i].shape))
            
        self.y_lateral_synapse_diff = np.zeros(self.y_lateral_weight.shape)
        self.y_lateral_synapse_factor = np.ones(self.y_lateral_weight.shape)
        
        self.y_inhibit_synapse_diff = np.zeros(self.y_inhibit_weight.shape)
        self.y_inhibit_synapse_factor = np.ones(self.y_inhibit_weight.shape)
        
        # z weights
        self.z_bottom_up_weight = []
        self.z_firing_age = []
        for i in range(self.z_area_num):
            self.z_bottom_up_weight.append(np.zeros((self.y_neuron_num, self.z_neuron_num[i])))
            self.z_firing_age.append(np.zeros((1, self.z_neuron_num[i])))
        # responses
        self.x_response = np.zeros((1, self.x_neuron_num))
        # pre lateral response is bottom up + top down, used to get lateral
        # pre response is bottom up + top down + lateral
        self.y_bottom_up_percent = 1/2
        self.y_top_down_percent = 1/2
        self.y_lateral_percent = 1/2
        
        self.y_bottom_up_response = np.zeros((1, self.y_neuron_num))
        self.y_top_down_response = np.zeros((self.z_area_num, self.y_neuron_num))
        self.y_pre_lateral_response = np.zeros((1, self.y_neuron_num))
        self.y_lateral_response = np.zeros((1, self.y_neuron_num))
        self.y_pre_response = np.zeros((1, self.y_neuron_num))
        
        self.y_response = np.zeros((1, self.y_neuron_num))
        self.z_response = []
        for i in range(self.z_area_num):
            self.z_response.append(np.zeros((1, self.z_neuron_num[i])))

4.3.2 Расчет отклика

Основываясь на приведенном выше рисунке и описании в предыдущем разделе, входные данные функции расчета полного отклика включают в себя: входной вектор input_vec, вектор веса weight_vec и фактор внимания synapse_factor. Сначала умножьте каждый элемент фактора внимания на соответствующий элемент входного вектора, затем вычислите его нормализованный единичный вектор, а затем объедините входной вектор нормализованного объединенного фактора внимания с тем же нормализованным весовым скалярным произведением вектора, чтобы получить окончательный ответ [точечный продукт двух нормализованных векторов - это косинус прилежащего угла исходного вектораcos(θ)cos(\theta)].

def compute_response(input_vec, weight_vec, synapse_factor):
    """
    input_vec is of shape 1x input_dim
    weight_vec is of shape input_dim x neuron_num
    syanpse_factor is of shape input_dim x neuron_num
    """
    
    _, neuron_num = weight_vec.shape
    _, input_dim = input_vec.shape
    
    # reshape input to neuron_num x input_dim
    temp_input = np.tile(input_vec, (neuron_num, 1))
    temp_input = temp_input*synapse_factor.T
    
    # normalize input
    temp_input_norm = np.sqrt(np.sum(temp_input*temp_input, axis=1))
    temp_input_norm[temp_input_norm == 0] = 1
    
    temp_input = temp_input/np.tile(temp_input_norm.reshape(-1, 1), (1, input_dim))
    
    # normalize weight
    weight_vec_normalized = weight_vec*synapse_factor
#     plt.imshow(weight_vec_normalized)
#     plt.show()
    weight_vec_norm = np.sqrt(np.sum(weight_vec_normalized*weight_vec_normalized, axis=0))
    weight_vec_norm[weight_vec_norm == 0] = 1
    
    weight_vec_normalized = weight_vec_normalized/np.tile(weight_vec_norm, (input_dim, 1))
    
    output_vec = np.zeros((1, neuron_num))
    for i in range(neuron_num):
        output_vec[0, i] = np.dot(temp_input[i,:].reshape(1, -1), weight_vec_normalized[:, i].reshape(-1, 1))[0,0]
    return output_vec

4.3.3 ответ топ-k конкурентов

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

        self.x_response = training_image.reshape(1, -1)
        for i in range(self.z_area_num):
            self.z_response[i] = np.zeros(self.z_response[i].shape)
            self.z_response[i][0,true_z[i]] = 1
        self.x_response = preprocess(self.x_response)
         # compute response
        self.y_bottom_up_response = compute_response(self.x_response, 
                                                     self.y_bottom_up_weight, 
                                                     self.y_bottom_up_synapse_factor)
        for i in range(self.z_area_num):
            self.y_top_down_response[i] = compute_response(self.z_response[i], 
                                                          self.y_top_down_weight[i],
                                                          self.y_top_down_synapse_factor[i])
        # top-down + bottom-up response    
        self.y_pre_lateral_response = (self.y_bottom_up_percent*self.y_bottom_up_response + 
                                       self.y_top_down_percent*np.mean(self.y_top_down_response, axis=0).reshape(1,-1))/(self.y_bottom_up_percent + self.y_top_down_percent)
        

        # 侧边响应    
        self.y_lateral_response = compute_response(self.y_pre_lateral_response,
                                                  self.y_lateral_weight,
                                                  self.y_lateral_synapse_factor)
        self.y_pre_response = ((self.y_bottom_up_percent + self.y_top_down_percent)*self.y_pre_lateral_response + 
                               self.y_lateral_percent*self.y_lateral_response)
        
        self.y_response = top_k_competition(self.y_pre_response,
                                            self.y_top_down_response,
                                            self.y_inhibit_weight,
                                            self.y_inhibit_synapse_factor,
                                            self.y_top_k)
        

Нам нужно дополнительно рассчитать количество активированных нейронов в конкурсе top-k, чтобы узнать, какие нейроны могут использовать текущую выборку для обновления параметров. При расчете конкуренции в топ-к используются преимуществаinhibit weight.Процедура следующая:

def top_k_competition(response_input, top_down_response, inhibit_weight, inhibit_synapse_factor, top_k):
    """
    TODO: there are two ways to do things
    1: if a neuron is within the synapse, then include that neuron in top-k
    2: if a neuron is within the synapse and the weight is > 0.5, then
    include that neuron in top-k
    this version does things in the 1st way
    
    response_input is of size 1xneuron_num
    """
    response_output = np.zeros(response_input.shape)
    _, neuron_num = response_input.shape
    top_down_flag = np.ones((1, neuron_num))
    for i in range(len(top_down_response)):
        top_down_flag = top_down_flag*top_down_response[i]
    for i in range(neuron_num):
        curr_response = response_input[0,i]
        curr_mask = (inhibit_synapse_factor[:,i] > 0)
        compare_response = response_input*curr_mask.T.reshape(1, -1)
        compare_response[0,i] = curr_response
        neuron_id = np.argsort(-compare_response.reshape(-1))      
        
        for j in range(top_k):
            if len(top_down_response) != 0:
                if neuron_id[j] == i and top_down_flag[0,i]>0:
                    response_output[0,i] = 1
                    break
            elif neuron_id[j] == i:
                response_output[0,i] = 1
                break            
    return response_output

4.3.4 Обновление параметров

В соответствии с функцией соревнования top-k можно рассчитать активные в данный момент нейроны, и каждый вес можно обновить в соответствии с правилом обучения Хебба.

Здесь необходимо отметить два момента:

  1. В этом примере для X выбрано только внимание, то есть значение bottom_up_synapse_factor имеет значение, и оно обновляется в режиме онлайн через промежуточную переменную synapse diff; вход Z не имеет выбора внимания, и все элементы synapse_factor фиксируются на 1.
  2. Скорость обучения lr является функцией частоты доступа и параметров забывания. Она адаптивно регулируется при обучении. Статическая фиксированная скорость обучения не используется для разумного распределения весов исторических данных и текущих данных, чтобы лучше отслеживать динамику входная среда пол. Функция для получения скорости обучения в этом примере (fireing_age — это количество активаций нейрона):

在这里插入图片描述

Процедура следующая:

        # hebbian learning and synapse maitenance
        for i in range(self.y_neuron_num):
            if self.y_response[0,i] == 1: # firing neuron, currently set response to 1
                if self.y_lsn_flag[0,i] == 0:
                    self.y_lsn_flag[0,i] = 1
                    self.y_firing_age[0,i] = 0
                lr = get_learning_rate(self.y_firing_age[0,i]) # learning rate
                # bottom-up weight and synapse factor
                self.y_bottom_up_weight[:,i] = (1-lr)*self.y_bottom_up_weight[:,i] + lr*self.x_response.reshape(-1)
                self.y_bottom_up_synapse_diff[:,i] = ((1-lr)*self.y_bottom_up_synapse_diff[:,i]+
                                                      lr*(np.abs(self.y_bottom_up_weight[:,i]-self.x_response.reshape(-1))))
                if self.y_synapse_flag>0 and self.y_firing_age[0,i] > self.y_synapse_age:
                    self.y_bottom_up_synapse_factor[:,i] = get_synapse_factor(self.y_bottom_up_synapse_diff[:,i],
                                                                              self.y_bottom_up_synapse_factor[:,i],
                                                                              self.y_synapse_coefficient)
                
                # top-down weight and synapse factor
                for j in range(self.z_area_num):
                    self.y_top_down_weight[j][:,i] = (1-lr)*self.y_top_down_weight[j][:,i] + lr*self.z_response[j].reshape(-1)
                    self.y_top_down_synapse_diff[j][:,i] = ((1-lr)*self.y_top_down_synapse_diff[j][:,i] + 
                                                            lr*np.abs(self.y_top_down_weight[j][:,i]-self.z_response[j].reshape(-1)))
                    if (self.y_synapse_flag>1) and (self.y_firing_age[0,i]>self.y_synapse_age):
                        self.y_top_down_synapse_factor[j][:,i] = get_synapse_factor(self.y_top_down_synapse_diff[j][:,i],
                                                                                    self.y_top_down_synapse_factor[j][:,i],
                                                                                    self.y_synapse_coefficient)
                # lateral weight and synapse factor
                # lateral exitation connection only exists within firing neurons
                self.y_lateral_weight[:,i] = (1-lr)*self.y_lateral_weight[:,i]+lr*self.y_response.reshape(-1)
                self.y_lateral_synapse_diff[:,i] = ((1-lr)*self.y_lateral_synapse_diff[:,i] + 
                                                    lr*np.abs(self.y_lateral_weight[:,i] - self.y_response.reshape(-1)))
                if (self.y_synapse_flag > 2) and (self.y_firing_age[0,i]>self.y_synapse_age):
                    self.y_lateral_synapse_factor[:,i] = get_synapse_factor(self.y_lateral_synapse_diff[:,i],
                                                                           self.y_lateral_synapse_factor[:,i],
                                                                           self.y_synapse_coefficient)
                self.y_firing_age[0,i] = self.y_firing_age[0,i] + 1
            elif self.y_lsn_flag[0,i] == 0: # initialization stage neuron is always updating
                lr = get_learning_rate(self.y_firing_age[0,i])
                normed_input = self.x_response.reshape(-1, 1)*self.y_bottom_up_synapse_factor[:,i].reshape(-1, 1)
                self.y_bottom_up_weight[:,i] = (1-lr)*self.y_bottom_up_weight[:,i]+lr*normed_input.reshape(-1)
                self.y_bottom_up_weight[:,i] = self.y_bottom_up_weight[:,i]*self.y_bottom_up_synapse_factor[:,i]
                self.y_bottom_up_synapse_diff[:,i] = ((1-lr)*self.y_bottom_up_synapse_diff[:,i] +
                                                     lr*np.abs(self.y_bottom_up_weight[:,i] - normed_input.reshape(-1)))
                
                if self.y_synapse_flag>0 and self.y_firing_age[0,i] > self.y_synapse_age:
                    self.y_bottom_up_synapse_factor[:,i] = get_synapse_factor(self.y_bottom_up_synapse_diff[:,i],
                                                                          self.y_bottom_up_synapse_factor[:,i],
                                                                          self.y_synapse_coefficient)  
                # top-down weight and synapse factor
                for j in range(self.z_area_num):
                    self.y_top_down_weight[j][:,i] = (1-lr)*self.y_top_down_weight[j][:,i] + lr*self.z_response[j].reshape(-1)
                    self.y_top_down_synapse_diff[j][:,i] = ((1-lr)*self.y_top_down_synapse_diff[j][:,i] + 
                                                            lr*np.abs(self.y_top_down_weight[j][:,i]-self.z_response[j].reshape(-1)))
                    if (self.y_synapse_flag>1) and (self.y_firing_age[0,i]>self.y_synapse_age):
                        self.y_top_down_synapse_factor[j][:,i] = get_synapse_factor(self.y_top_down_synapse_diff[j][:,i],
                                                                                    self.y_top_down_synapse_factor[j][:,i],
                                                                                    self.y_synapse_coefficient)
                        
                # lateral weight and synapse factor
                # lateral exitation connection only exists within firing neurons
                self.y_lateral_weight[:,i] = (1-lr)*self.y_lateral_weight[:,i]+lr*self.y_response.reshape(-1)
                self.y_lateral_synapse_diff[:,i] = ((1-lr)*self.y_lateral_synapse_diff[:,i] + 
                                                    lr*np.abs(self.y_lateral_weight[:,i] - self.y_response.reshape(-1)))
                if (self.y_synapse_flag > 2) and (self.y_firing_age[0,i]>self.y_synapse_age):
                    self.y_lateral_synapse_factor[:,i] = get_synapse_factor(self.y_lateral_synapse_diff[:,i],
                                                                           self.y_lateral_synapse_factor[:,i],
                                                                           self.y_synapse_coefficient)   
            else:
                lr = get_learning_rate(self.y_inhibit_age[0,i])
                temp = np.zeros(self.y_inhibit_synapse_factor.shape)
                for j in range(self.y_neuron_num):
                    temp[:,j] = self.y_pre_lateral_response.reshape(-1)*self.y_inhibit_synapse_factor[:,j]
                    temp[:,j] = (temp[:,j] > self.y_pre_lateral_response[0,i])
                self.y_inhibit_weight[:,i] = (1-lr)*self.y_inhibit_weight[:,i]+lr*temp[:,i]
                self.y_inhibit_synapse_diff[:,i] = ((1-lr)*self.y_inhibit_synapse_diff[:,i] + 
                                                   lr*np.abs(self.y_inhibit_weight[:,i]-temp[:,i]))
                if (self.y_synapse_flag > 3) and (self.y_firing_age[0,i]>self.y_synapse_age):
                    self.y_inhibit_synapse_factor[:,i] = get_synapse_factor(self.y_inhibit_synapse_diff[:,i],
                                                                           self.y_inhibit_synapse_factor[:,i],
                                                                           self.y_synapse_coefficient)
                self.y_inhibit_age[0,i] = self.y_inhibit_age[0,i] + 1
        ## z neuron learning
        for area_idx in range(self.z_area_num):
            for i in range(self.z_neuron_num[area_idx]):
                if self.z_response[area_idx][0,i] == 1:
                    lr = get_learning_rate(self.z_firing_age[area_idx][0,i])
                    self.z_bottom_up_weight[area_idx][:,i] = (1-lr)*self.z_bottom_up_weight[area_idx][:,i]+lr*self.y_response.reshape(-1)
                    self.z_firing_age[area_idx][0,i] = self.z_firing_age[area_idx][0,i] + 1

4.3.5 Использование DN

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

При заданном входе X программа для вычисления выхода Z выглядит следующим образом:

    def dn_test(self, test_image):
        self.x_response = test_image.reshape(1, -1)
        self.x_response = preprocess(self.x_response)
        self.y_bottom_up_response = compute_response(self.x_response, 
                                                     self.y_bottom_up_weight, 
                                                     self.y_bottom_up_synapse_factor)
        self.y_pre_lateral_response = self.y_bottom_up_response
        self.y_lateral_response = compute_response(self.y_pre_lateral_response,
                                                   self.y_lateral_weight,
                                                   self.y_lateral_synapse_factor)
        self.y_pre_response = ((self.y_bottom_up_percent*self.y_pre_lateral_response+
                               self.y_lateral_percent*self.y_lateral_response)/(self.y_bottom_up_percent+
                                                                               self.y_lateral_percent))
        self.y_response = top_k_competition(self.y_pre_response, 
                                            [], 
                                            self.y_inhibit_weight, 
                                            self.y_inhibit_synapse_factor, 
                                            self.y_top_k)
        z_output = []
        for i in range(self.z_area_num):
            self.z_response[i] = compute_response(self.y_response,
                                                  self.z_bottom_up_weight[i],
                                                  np.ones(self.z_bottom_up_weight[i].shape))
            z_output_i = np.argmax(self.z_response[i])
            z_output.append(z_output_i)
        return np.array(z_output)

4.3.5 Адаптивный рост нейронов DN

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

def dn_split(dn, split_num, split_firing_age):
    input_dim = dn.x_neuron_num
    y_top_k = dn.y_top_k
    z_neuron_num = dn.z_neuron_num
    y_neuron_num = dn.y_neuron_num*split_num

    new_to_old_index = np.zeros(y_neuron_num, dtype=np.int)
    for i in range(dn.y_neuron_num):
        start_ind = i*split_num
        end_ind = (i+1)*split_num
        new_to_old_index[start_ind:end_ind] = i
    new_to_old_index = new_to_old_index.tolist()
    new_dn = DN(input_dim, y_neuron_num, y_top_k, z_neuron_num)
    for i in range(new_dn.y_neuron_num):
        j = new_to_old_index[i]
        new_dn.y_lsn_flag[0,i] = dn.y_lsn_flag[0,j]
        new_dn.y_firing_age[0,i] = split_firing_age
        new_dn.y_inhibit_age[0,i] = split_firing_age
        
        new_dn.y_bottom_up_weight[:,i] = (dn.y_bottom_up_weight[:,j] + 
                                          generate_rand_mutate(dn.y_bottom_up_weight[:,j].shape))
        new_dn.y_bottom_up_weight[:,i] = (dn.y_bottom_up_weight[:,j])/np.max(new_dn.y_bottom_up_weight[:,j])
        for z_ind in range(new_dn.z_area_num):
            new_dn.y_top_down_weight[z_ind][:,i] = (dn.y_top_down_weight[z_ind][:,j]+
                                                    generate_rand_mutate(dn.y_top_down_weight[z_ind][:,j].shape))
            new_dn.y_top_down_weight[z_ind][:,i] = new_dn.y_top_down_weight[z_ind][:,i]/np.max(new_dn.y_top_down_weight[z_ind][:,i])
        new_dn.y_lateral_weight[:,i] = dn.y_lateral_weight[new_to_old_index, j]
        new_dn.y_inhibit_weight[:,i] = (dn.y_inhibit_weight[new_to_old_index, j]+
                                       generate_rand_mutate(dn.y_inhibit_weight[new_to_old_index, j].shape))
        new_dn.y_inhibit_weight[:,i] = new_dn.y_inhibit_weight[:,i]/np.max(new_dn.y_inhibit_weight[:,i])
        
        new_dn.y_bottom_up_synapse_diff[:,i] = dn.y_bottom_up_synapse_diff[:,j]
        new_dn.y_bottom_up_synapse_factor[:,i] = np.ones(dn.y_bottom_up_synapse_factor[:,j].shape)
        
        for z_ind in range(new_dn.z_area_num):
            new_dn.y_top_down_synapse_diff[z_ind][:,i] = dn.y_top_down_synapse_diff[z_ind][:,j]
            new_dn.y_top_down_synapse_factor[z_ind][:,i] = np.ones(dn.y_top_down_synapse_factor[z_ind][:,j].shape)
        new_dn.y_lateral_synapse_diff[:,i] = dn.y_lateral_synapse_diff[new_to_old_index, j]
        new_dn.y_lateral_synapse_factor[:,i] = np.ones(dn.y_lateral_synapse_factor[new_to_old_index, j].shape)
        
        new_dn.y_inhibit_synapse_diff[:,i] = dn.y_inhibit_synapse_diff[new_to_old_index, j]
        new_dn.y_inhibit_synapse_factor[:,i] = np.ones(dn.y_inhibit_synapse_factor[new_to_old_index,j].shape)
        
        for z_ind in range(new_dn.z_area_num):
            new_dn.z_bottom_up_weight[z_ind][i,:] = dn.z_bottom_up_weight[z_ind][j,:]
            
    for z_ind in range(new_dn.z_area_num):
        new_dn.z_firing_age[z_ind] = np.ones(dn.z_firing_age[z_ind].shape)
    return new_dn
    

4.4 Результаты

Тренировочный эффект каждого шага показан ниже Мы обнаружили, что в середине есть три операции разделения, а конечное количество нейронов DN равно 25.33=225, итоговая точность теста составляет [0,99 0,962]. Мы заметим, что всякий раз, когда производительность сети сталкивается с узким местом, после того, как происходит разделение, производительность сети снова повышается. 500 training, current performance: [0.226 0.054] 1000 training, current performance: [0.278 0.068] 1500 training, current performance: [0.362 0.164] 2000 training, current performance: [0.41 0.17] 2500 training, current performance: [0.4 0.172] 3000 training, current performance: [0.442 0.182] 3500 training, current performance: [0.476 0.212] 4000 training, current performance: [0.48 0.226] 4500 training, current performance: [0.486 0.206] 5000 training, current performance: [0.466 0.242] 5500 training, current performance: [0.462 0.204] 6000 training, current performance: [0.48 0.232] 6500 training, current performance: [0.436 0.174] 7000 training, current performance: [0.522 0.256] splitting at 7263 7500 training, current performance: [0.444 0.292] 8000 training, current performance: [0.776 0.558] 8500 training, current performance: [0.8 0.558] 9000 training, current performance: [0.78 0.59] 9500 training, current performance: [0.8 0.574] 10000 training, current performance: [0.784 0.6 ] 10500 training, current performance: [0.794 0.586] 11000 training, current performance: [0.82 0.596] 11500 training, current performance: [0.824 0.614] 12000 training, current performance: [0.826 0.602] 12500 training, current performance: [0.818 0.58 ] splitting at 12804 13000 training, current performance: [0.688 0.444] 13500 training, current performance: [0.802 0.696] 14000 training, current performance: [0.922 0.882] 14500 training, current performance: [0.934 0.908] 15000 training, current performance: [0.92 0.9 ] 15500 training, current performance: [0.924 0.876] 16000 training, current performance: [0.96 0.922] 16500 training, current performance: [0.974 0.928] 17000 training, current performance: [0.988 0.954] 17500 training, current performance: [0.97 0.956] 18000 training, current performance: [0.984 0.95 ] 18500 training, current performance: [0.992 0.984] 19000 training, current performance: [0.988 0.956] 19500 training, current performance: [0.988 0.97 ] 20000 training, current performance: [0.996 0.97 ] 20500 training, current performance: [0.986 0.958] 21000 training, current performance: [0.99 0.956] 21500 training, current performance: [0.994 0.972] 22000 training, current performance: [0.994 0.978] 22500 training, current performance: [0.992 0.982] 23000 training, current performance: [0.992 0.978] 23500 training, current performance: [0.992 0.966] 24000 training, current performance: [0.99 0.958] 24500 training, current performance: [0.99 0.962] testing error is [0.996 0.975] DN y_bottom_up_weight печатается следующим образом по точкам матрицы 15x15, каждая точка матрицы представляет собой маленькую матрицу 19x19. 在这里插入图片描述

4.5 Программа [Загружено на github]

声明:本例子的程序是参照翁教授的学生Zejia Zheng的matlab代码写的。Прикрепить исходный адресgithub/ZejiaZheng/multiresolutionDN[matlab]

Я углубил свое понимание сетей разработки, переписав код Matlab в код Python. Я программа на Python, написанная в рамках интерактивной среды компиляции ноутбука jupyter, которая была загружена на github.github/huyanmingtoby/multiresolutionDN[python]

4.6 Анализ и обсуждение

Этот раздел (раздел 4) дополняет сеть разработки примером реализации [Where-What-Network]. Сеть обучается с использованием построенных данных изображения, а также меток местоположения и категории объектов в качестве входных данных для WWN. Во время обучения сама сеть развития претерпевает два митотических деления нейронов в слое развития, в результате чего получается 225 нейронов. Каждое разделение может значительно повысить точность теста. Наконец, y_bottom_up_weight также распечатывается, а веса каждого нейрона, связанные с входом X, распечатываются как 19x19, и обнаруживается, что они представляют собой серию паттернов, которые очень похожи на входное изображение. 5x25=125 для всех возможных позиций всех объектов. Идеальное количество нейронов — 125 для хранения всех возможных паттернов. При инициализации количество нейронов в DN равно 25, что явно мало, после одного митоза становится 25х3=75, что мало, после очередного митоза 75х3=225, что теоретически достаточно. точность теста очень высока [0,99 0,962]]. Однако необходимо объяснить одну вещь: фон выбирается случайным образом, и существует бесчисленное множество видов одного и того же объекта, помещенного на случайный фон в одном и том же месте. Окончательный эффект нейронов сети развития в 225 уже очень хорош, что указывает на то, что сеть развития может захватывать важную информацию (пиксели, связанные с объектом) и игнорировать эти фоновые пиксели, что является эффектом выбора внимания. Внимание нейрона выбирает вес так, чтобы он реагировал только на соответствующую область ввода, избегая таким образом влияния фонового шума.

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

5. Заключение

В этой статье сеть развития систематически представлена ​​на четырех уровнях, включая идеи, методы, алгоритмы и процедуры. Сеть развития имеетin-placeХарактерно, что каждый нейрон содержит все программы развития, поэтому мы сосредоточимся на инициализации, обучении и использовании нейрона. Программа развития каждого нейрона - это CCILCA. Чтобы четко описать идею DN, в этой статье анализ листовых компонентов разделен. Трудно увидеть завершение LCA. Но я думаю, что это полезно для ознакомления с идеями и методами DN. Я восстановлю сломанный LCA из этой статьи до полного алгоритма в другом блоге. Наконец, суб-WWN сети разработки используется для углубления понимания DN и, таким образом, для раскрытия более подробной информации о DN. Количество нейронов в слое развития DN адаптивно регулируется, и конечный эффект обучения также очень хорош. Кроме того, эта статья также включает в себя много личного мнения. Не обязательно подходит, добро пожаловать в общение. Теперь я разбираюсь со своими сомнениями по поводу DN следующим образом:

  • Оправдана ли забывчивость в DN, а человеческие черты просто хороши?
  • Можно ли заменить другими показателями расстояния без изменения автономной программы развития?cos(θ)cos(\theta)?
  • В конечном счете, DN по-прежнему хранит полученные знания в виде справочной таблицы, то есть . Действительно ли знания в человеческом мозгу существуют в этом состоянии памяти? Например, сети глубокого обучения и RBF будут использовать нелинейные функции для соответствия взаимосвязи между x и z, что, очевидно, является более эффективным способом [сначала отложить в сторону добавочное и последовательное обучение человека].Для более эффективного кодирования емкость модели, необходимая для функции представление будет меньше для того же количества информации.