Файл: Решение Для реализации алгоритма понадобятся следующие формулы.docx

ВУЗ: Не указан

Категория: Не указан

Дисциплина: Не указана

Добавлен: 25.10.2023

Просмотров: 27

Скачиваний: 2

ВНИМАНИЕ! Если данный файл нарушает Ваши авторские права, то обязательно сообщите нам.

Министерство науки и высшего образования РФ

Федеральное государственное бюджетное

образовательное учреждение высшего образования

«Курский государственный университет»

Кафедра программного

обеспечения и администрирования

информационных систем

Направление подготовки

математическое обеспечение и

администрирование

информационных систем

Форма обучения очная

Отчет

о выполнении лабораторной работы №7

Вариант 5

дисциплина «Основы теории нейронных сетей»

Выполнила:

студентка группы 413.1 Мвеемба Э.М.

Проверил:

д.ф.-м.н.,

профессор кафедры ПОиАИС Добрица В.П.

Курск, 2020

Задача 1.

Составить обучающую программу однослойной нейронной сети, интерпретирующей временной ряд, с 6 входными и одним выходным нейронами. Параметры обучающей программы: шаг обучения , предполагаемая точность , временной шаг , начальный момент , длина обучающей серии . Значения временного ряда вычисляются по данной временной функции: y(t) = t – cos t

Задача 2.

Провести обучение нейросети для того же временного ряда с адаптивным шагом обучения. Сравнить время обучения сетей в этих задачах с постоянным шагом обучения и с адаптивным шагом обучения.

Решение

Для реализации алгоритма понадобятся следующие формулы:

– среднеквадратичная ошибка нейросети для входного образа L.

– выходное значение нейросети, где – весовые коэффициенты, – значение пороговой функции.

– весовые коэффициенты, где
– предыдущие весовые коэффициенты, ???? – скорость обучения, – входное значение нейросети, , – эталонное и выходное значения нейросети.

– значение пороговой функции, где – предыдущее значение, – скорость обучения, , – эталонное и выходное значения нейросети.

Для реализации адаптивного шага понадобится формула нахождения адаптивного шага обучения:


Для выполнения условий теоремы Колмогорова сначала необходимо провести нормализацию, чтобы значения функции располагались в интервале [0, 1]. Данные преобразования производятся по формуле .

(Можно, но не обязательно, т.к. у Вас линейная функция активации. Если используется сигмоидная, то тогда это необходимо.)

Блок-схема алгоритма представлена на рисунке 1.



Рисунок 1 – Блок схема алгоритма
Схема полученной нейронной сети приведена на рисунке 2.


Рисунок 2 – Схема нейронной сети
На рисунке 3 приведен фрагмент обучающихся данных для нейронной сети.


Рисунок 3 – Фрагмент обучающих данных для нейронной сети
Результат работы программы приведен на рисунке 4.


Рисунок 4 – Результат работы программы


Вывод: прогнозирование нейросетью, обученной с адаптивным шагом, дает более точный результат, чем прогнозирование нейросетью, обученной без адаптивного шага обучения.
Листинг программы

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using System.Threading.Tasks;
namespace lab7

{

class Program

{


static private List OtvetW = new List();

static private double OtvetT = 0;

static private double E = 0.01;

static void Main(string[] args)

{

double[,] mas1 = y1();

Console.WriteLine("С постоянным коэффициентом скорости обучения");

WithoutAdaptive(mas1);

Proverka();

Console.WriteLine("С адаптивным коэффициентом скорости обучения");

Adaptive(mas1);

Proverka();

Console.ReadKey();

}
static double[,] y1()

{

double[,] mas = new double[993, 7];
double t = 0;

Console.WriteLine("a1\ta2\ta3\ta4\ta5\ta6\ty");

for (int i = 0; i < 993; i++)

{

double p = t;

for (int j = 0; j < 7; j++)

{

mas[i, j] = p - Math.Cos(p);

mas[i, j] = (mas[i, j] + 1) / 105; //Проводим нормализацию

p += 0.1;

}

Console.WriteLine("{0:f5}\t{1:f5}\t{2:f5}\t{3:f5}\t{4:f5}\t{5:f5}\t{6:f5}", mas[i, 0], mas[i, 1], mas[i, 2], mas[i, 3], mas[i, 4], mas[i, 5], mas[i, 6]);

t += 0.1;

}
return mas;

}
static double FuncA(double x) //Функция активации

{

return 1.0 / (1 + Math.Exp(-x));

}
static void WithoutAdaptive(double[,] nabor)

{

double alpha = 0.1;

List W = new List();

Random random = new Random();

for (int i = 0; i < 6; i++)

W.Add(0);
double T = Math.Abs(0), TempE = 10;

double LastE = 0;
int ch = 0;
while ((TempE >= E) && (ch < 100000))

{

TempE = 0;

for (int row = 0; row < 993; row++)

{

double TempY = 0;

for (int i = 0; i < 6; i++)

TempY += nabor[row, i] * W[i]; //вычисляем значение для каждой строки

TempY -= T;
TempY = FuncA(TempY); //Функция активации
TempE += Math.Pow((nabor[row, 6] - TempY), 2);//квадратичное отклонение
for (int k = 0; k < 6; k++)

W[k] = W[k] + alpha * (nabor[row, 6] - TempY) * nabor[row, k]; //(1)

T -= alpha * (nabor[row, 6] - TempY); //(2)

}

TempE *= 0.5;

if (Math.Abs(TempE - LastE) < 0.00001)

break;
LastE = TempE;

ch += 1;

}
string result = "";

for (int k = 0; k < 6; k++)

{

if (W[k] >= 0)

result += "x" + (k + 1).ToString() + " * " + Math.Round(W[k], 5).ToString() + " + ";

else

result += "x" + (k + 1).ToString() + " * (" + Math.Round(W[k], 5).ToString() + ") + ";

}

result = result.Substring(0, result.LastIndexOf("+"));

if (T >= 0)

result += "- " + Math.Round(T, 5).ToString();

else

result += "+ " + Math.Abs(Math.Round(T, 5)).ToString();
result = "y = " + result;

OtvetW = W;

OtvetT = T;

Console.WriteLine(result);

}
static void Proverka()

{

double p = 0;

double t = 99.3;

Console.WriteLine("\nПроверка:");

for (int i = 0; i < 6; i++)

{
var z = t - Math.Cos(t);

Console.Write("{0:f5}\t", (z + 1) / 105);

p += (z + 1) / 105 * OtvetW[i];

t += 0.1;
}

p -= OtvetT;

Console.WriteLine();

Console.WriteLine("Ожидаемый результат: {0}", t - Math.Cos(t));

Console.WriteLine("Полученный результат: {0}", FuncA(p) * 105 - 1); //Возвращаемся к исходному значению

Console.WriteLine();

}
static void Adaptive(double[,] nabor)

{

List W = new List();

Random random = new Random();

for (int i = 0; i < 6; i++)

W.Add(0);
double T = 0, TempE = 10;

double LastE = 0;
int ch = 0;
while ((TempE >= E) && (ch < 100000))

{

TempE = 0;

for (int row = 0; row < 993; row++)

{

double alpha = 0;

for (int col = 0; col < 6; col++)

alpha += Math.Pow(nabor[row, col], 2);

alpha = 1 / (1 + alpha); // (5)
double TempY = 0;

for (int i = 0; i < 6; i++)

TempY += nabor[row, i] * W[i]; //вычисляем значение для каждой строки

TempY -= T;
TempY = FuncA(TempY); //Функция активации
TempE += Math.Pow((nabor[row, 2] - TempY), 2);//квадратичное отклонение
for (int k = 0; k < 6; k++)

W[k] = W[k] + alpha * (nabor[row, 6] - TempY) * nabor[row, k]; //(1)
T -= alpha * (nabor[row, 6] - TempY); //(2)

}
TempE *= 0.5;

if (Math.Abs(TempE - LastE) < 0.00001)

break;
LastE = TempE;

ch += 1;

}
string result = "";

for (int k = 0; k < 6; k++)

{

if (W[k] >= 0)

result += "x" + (k + 1).ToString() + " * " + Math.Round(W[k], 5).ToString() + " + ";

else

result += "x" + (k + 1).ToString() + "* (" + Math.Round(W[k], 5).ToString() + ") + ";

}

result = result.Substring(0, result.LastIndexOf("+"));

if (T >= 0)

result += "- " + Math.Round(T, 2).ToString();

else

result += "+ " + Math.Abs(Math.Round(T, 5)).ToString();

result = "y = " + result;

OtvetW = W;

OtvetT = T;

Console.WriteLine(result);

}

}

}