В библиотеке Synaptic управление весами нейронной сети играет ключевую роль в скорости обучения и качестве получаемых результатов. Начальные веса определяют, как сеть начнёт обучение, и влияют на возможность сети избежать локальных минимумов функции потерь.
В Synaptic каждый нейрон имеет входящие
синаптические связи, каждая из которых содержит вес
(weight). Вес определяет силу влияния входного сигнала на
нейрон. По умолчанию при создании сети веса инициализируются случайными
числами в диапазоне [-1, 1], что обеспечивает базовую
вариативность сигналов и предотвращает симметричность обучения.
Пример создания простого нейрона с произвольными весами:
const synaptic = require('synaptic');
const Neuron = synaptic.Neuron;
let neuron = new Neuron();
console.log(neuron.connections.inputs); // пустой объект перед соединениями
После соединения с другими нейронами веса можно установить вручную или модифицировать автоматически.
Проекция (Projection) в Synaptic
представляет собой набор синаптических соединений между слоями. При
создании соединения между двумя слоями (Layer)
автоматически генерируются веса для каждой связи.
Настройка этих весов важна для:
Пример создания проекции между слоями:
const Layer = synaptic.Layer;
let inputLayer = new Layer(3);
let hiddenLayer = new Layer(4);
inputLayer.project(hiddenLayer); // создаёт проекцию с начальной инициализацией весов
По умолчанию project создаёт рандомизированные
веса в диапазоне [-1, 1], но библиотека позволяет задавать
собственные начальные веса.
Для точного контроля над весами используется метод
connect, позволяющий задавать сразу все веса
проекции.
Пример:
let weights = [
[0.2, -0.5, 0.1, 0.0],
[0.7, 0.1, -0.3, 0.4],
[-0.4, 0.9, 0.2, -0.1]
];
for (let i = 0; i < inputLayer.list.length; i++) {
for (let j = 0; j < hiddenLayer.list.length; j++) {
inputLayer.list[i].project(hiddenLayer.list[j], weights[i][j]);
}
}
Здесь каждый входной нейрон получает индивидуально заданный вес для каждого соединения, что позволяет моделировать специфическую начальную конфигурацию сети.
Для больших сетей часто используются статистические распределения для начальных весов: нормальное (Гаусса) или равномерное. В JavaScript можно реализовать это с помощью функции генерации случайных чисел с требуемыми параметрами:
function randomNormal(mean = 0, stdDev = 1) {
let u = 0, v = 0;
while(u === 0) u = Math.random();
while(v === 0) v = Math.random();
let num = Math.sqrt(-2.0 * Math.log(u)) * Math.cos(2.0 * Math.PI * v);
return num * stdDev + mean;
}
// Применение к весам проекции
inputLayer.list.forEach(inputNeuron => {
inputNeuron.connections.projected.forEach(conn => {
conn.weight = randomNormal(0, 0.1);
});
});
Такой подход обеспечивает стабильное обучение и уменьшает вероятность сильных перепадов сигналов в начальной фазе.
Важной практикой является масштабирование начальных весов в зависимости от количества входов нейрона. Для слоев с большим числом нейронов слишком большие веса могут привести к насыщению активации, а слишком маленькие — к затуханию градиента. Рекомендуемая формула для нормализации:
[ w_i = ]
Применение в Synaptic:
inputLayer.list.forEach(neuron => {
neuron.connections.projected.forEach(conn => {
conn.weight = (Math.random() * 2 - 1) / Math.sqrt(inputLayer.list.length);
});
});
Весы можно изменять в любой момент обучения, что позволяет экспериментировать с адаптивной инициализацией или динамическим пересемплированием:
hiddenLayer.list.forEach(neuron => {
neuron.connections.inputs.forEach(conn => {
conn.weight *= 0.9; // лёгкое уменьшение веса
});
});
Это часто используется для регуляризации и предотвращения переобучения.
В рекуррентных сетях, создаваемых через Synaptic, веса связей между временными шагами также подлежат инициализации. Рекомендуется применять симметричное распределение с малой дисперсией, чтобы сигналы не взрывались при распространении через временные слои.
// Пример для рекуррентного слоя
const Layer = synaptic.Layer;
let recurrentLayer = new Layer(5);
recurrentLayer.list.forEach(neuron => {
neuron.connections.projected.forEach(conn => {
conn.weight = (Math.random() * 2 - 1) * 0.05;
});
});
Эти методы обеспечивают гибкость и контроль над процессом обучения, делая Synaptic мощным инструментом для экспериментирования с различными архитектурами нейронных сетей.