Некоторое время назад, приступив к изучению нейросетей (путем их программирования), я встал в тупик и попросил помощи здесь: Странное поведение нейросети. Спасибо всем, кто помог, это сдвинуло меня с мертвой точки.
Доложу по пунктам, как у меня продвигаются дела, может быть, мой опыт будет кому-то интересен.
-
Мне посоветовали сделать воронкообразную структуру сети и использовать dropout. После того, как я это сделал и стал подавать разумную обучающую выборку, сеть стала обучаться, «переобучение» пропало. Dropout запрограммировал с возможностью делать разные вероятности выпадания на разных слоях.
-
У меня на входе - вектора от реального физического процесса, поэтому нельзя гарантировать отсутствие корреляции между членами вектора. Скорее - наоборот. Поэтому сеть в классическом варианте не работает и я пошел по пути создания доп. настроек.
2.1. Во-первых, конечно, есть сильная зависимость качества обучения от к-та скорости обучения. Я сделал его линейно зависимым от функционала ошибки и от целевого вектора.
2.2. На обучающую выборку я накладываю шум, с равномерным или с нормальным распределением. Интуитивно чувствую, что это правильно.
2.3. Параметризовал функции активации. В случае сигмоиды и гиперболического тангенса ввел к-т при показателе экспоненты. Опыт показал, что зависимость обучаемости от этого параметра - очень сильная, при a=1 у меня просто ничего не работает. Параметр задаю разный на выходном слое и на прочих слоях.
2.4. Ощутил, что функции активации надо ставить разные на выходном слое и на прочих слоях.
-
Общий алгоритм сделал такой. Беру маленькую обучающую выборку, как только ошибка n раз подряд оказывается меньше некоторого уровня, подбрасываю в выборку еще 1 вектор и т.д. Вывожу таблицу со статистикой, в которой видно, какие вектора дают большие ошибки, и делаю из этого вывод, что я для них назначил неправильный целевой вектор.
-
До сих пор у меня получалось только классифицировать. Только с 3-мя целевыми векторами, соответствующим качествам работы исследуемого узла «хорошо», «подозрительно» и «скоро будет поломка». Меня это не устраивало, хотелось получить результат, по многобалльной шкале. Я решил оттолкнуться от задачи аппроксимации нейросетью функции. Сделал простейшую сеть, 1 нейрон на входе, 100 - в скрытом слое и 1 - на выходе. Сколько не бился, даже вычисление параболы не заработало (почему, интересно?).
Тогда у меня возникла идея, я стал делать так:
- логарифмирую целевой вектор перед его применением,
- использую логарифмическую целевую функцию.
Все заработало; по крайней мере, сеть считает степенные функции, а также находит обратные функции. И с многомерным случаем тоже работает (когда на входе не скаляр).
Интересно, это я придумал логарифмировать, или я изобрел велосипед?
Сейчас задумал сделать фильтр сигнала на базе своих старых наработок, результаты которых собираюсь скармливать нейросети. Если кому-нибудь будет интересно, тоже напишу.