Нейронная сеть на JavaScript в 30 строк кода

Нейронная сеть на JavaScript в 30 строк кода

https://t.me/bookflow

В этой статье будет показано, как создать и обучить нейронную сеть на JavaScript, используя Synaptic.js. Этот пакет позволяет реализовывать глубокое обучение в Node.js и в браузере. Будет создана простейшая возможная нейронная сеть — та, которой удается выполнить XOR операцию.

Перевод статьи «How to create a Neural Network in JavaScript in only 30 lines of code». Автор — Per Harald Borgen. Ссылка на оригинал — в подвале статьи. 

Вы можете видеть созданный мною интерактивный Scrimba туториал:

нейронная сеть на javascript


В Scribma туториале вы можете поиграться с сетью. Но перед тем, как посмотреть на код, давайте вспомним основы нейронных сетей.


Нейроны и синапсы

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

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

Круг ниже показывает сигмоидный нейрон. На входе — 5, на выходе — 1. Стрелочки называются синапсами, они соединяют нейрон с другими слоями в нейросети.

сигмоидный нейрон


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

Слева можно видеть два плюс одно значения. Зеленые числа — значения 1 и 0. Параметр сдвига -2 — коричневое число. Сначала входные числа умножаются на соответствующие им веса 7 и 3 соответственно. Значения весов представляют синие числа.

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

веса и смещения - нейронная сеть JS


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

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

нейронная сеть


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

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

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


Код нейросети JavaScript

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

Если вам трудно представить, что такое слой, посмотрите еще на скринкаст.

const { Layer, Network } = window.synaptic;
var inputLayer = new Layer(2);
var hiddenLayer = new Layer(3);
var outputLayer = new Layer(1);

Далее соединяем эти слои вместе и создаем инстанс новой сети, как показано ниже:

inputLayer.project(hiddenLayer);
hiddenLayer.project(outputLayer);
var myNetwork = new Network({
 input: inputLayer,
 hidden: [hiddenLayer],
 output: outputLayer
});

У нас получилась сеть с 2-3-1 нейронами в входном, скрытом и выходном слое, соответственно. Архитектура этой сети показана ниже:

XOR функция


Теперь давайте обучим нашу сеть:

// train the network - learn XOR
var learningRate = .3;
for (var i = 0; i < 20000; i++) {
  // 0,0 => 0
  myNetwork.activate([0,0]);
  myNetwork.propagate(learningRate, [0]);
  // 0,1 => 1
  myNetwork.activate([0,1]);
  myNetwork.propagate(learningRate, [1]);
  // 1,0 => 1
  myNetwork.activate([1,0]);
  myNetwork.propagate(learningRate, [1]);
  // 1,1 => 0
  myNetwork.activate([1,1]);
  myNetwork.propagate(learningRate, [0]);
}

Запускаем сеть 20 000 раз. Каждый раз распространяемся в прямом и обратном направлении четыре раза, проходя через четыре возможных входа для этой сети: [0,0], [0,1], [1,0], [1,1].

Начинаем с команды myNetwork.activate([0,0]), где [0,0] — данные, которые посылаются в сеть. Это прямое распространение, которое также называется активизацией сети. После каждого прямого распространения требуется сделать и обратное, тогда сеть обновит свои веса и свдиг.

Обратное распротстранение осуществляется командой myNetwork.propagate(learningRate, [0]). Параметр learningRate — константа, которая говорит сети, насколько каждый раз нужно изменять веса. Второй параметр — 0 представляет корректный ответ для заданного входа [0,0].

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

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

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

console.log(myNetwork.activate([0,0])); 
-> [0.015020775950893527]
console.log(myNetwork.activate([0,1]));
->[0.9815816381088985]
console.log(myNetwork.activate([1,0]));
-> [0.9871822457132193]
console.log(myNetwork.activate([1,1]));
-> [0.012950087641929467]

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

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




Report Page