- •Санкт-Петербург 2024
- •Листинг 2 – Создание эталонных образов
- •Листинг 3 – Визуализация эталонных образов
- •Листинг 4 – Создание зашумленных образов
- •Листинг 5 – Визуализация зашумленных образов.
- •Листинг 6 – Создание сети Хопфилда
- •Листинг 7 – Выполнение предсказаний
- •Листинг 8 – Визуализация неверно восстановленных изображений
- •Листинг 9 – Вычисление ошибки восстановления
- •Листинг 11 – Выполнение предсказания для зашумленного образа
Листинг 4 – Создание зашумленных образов
def make_a_noise(figure,noise):
origin = figure.copy()
for i in range (0,noise):
x = random.randint(0, 13)
y = random.randint(0, 13)
while (figure[x][y] != origin[x][y]):
x = random.randint(0, 13)
y = random.randint(0, 13)
figure[x][y] *= -1
return figure
noisy_rectangles = []
noisy_rombs = []
noisy_circles = []
noisy_ovals = []
noisy_triangles = []
noise = 10
while noise <= 100:
noisy_rectangles.append([make_a_noise(rectangle.copy(),noise),noise])
noisy_circles.append([make_a_noise(circle.copy(),noise),noise])
noisy_triangles.append([make_a_noise(triangle.copy(),noise),noise])
noise +=10
Для примера выполнена визуализация всех зашумленных изображения с помощью метода matshow() (Листинг 5). Перед каждой фигурой выведено название оригинального образа и уровень ошибки. Пример зашумленного образа приведен на Рисунке 2.
Рисунок 2 – Зашумленный квадрат
Листинг 5 – Визуализация зашумленных образов.
# Визуализация зашумленных образов.
def visualize_noisy(figure_list,name):
for fig in figure_list:
print(name,"\nОшибка -",fig[1])
plt.matshow(fig[0])
plt.show()
visualize_noisy(noisy_rectangles,'Квадрат')
visualize_noisy(noisy_circles,'Круг')
visualize_noisy(noisy_triangles,'Треугольник')
Создана сама нейронная сеть Хопфилда (Листинг 6). Класс HopfieldNetwork описывает размер сети (кол-во нейроном в слое) и матрицу весов. Класс содержит функцию train для обучения сети и predict для выполнения предсказания.
Обучение заключается в заполнении для эталонных образов матрицы весов, которая вычисляется по произведению эталонной матрицы на её транспонированный вариант. Для выполнения внешнего произведения методом outer массивы необходимо привести к одномерному виду, для чего используется метод flatten(). Диагональные элементы матрицы обнуляются при помощи функции fill_diagonal с параметром 0.
Предсказание выполняется следующим образом: передается зашумленная матрица. В течении 100 вычисляются состояния во всех нейронах, перемножением значений матрицы весов и полученного образа. Если значение состояния положительное, то на выходе записывается 1, иначе -1. Значения образа обновляются. Если зашумленный образ совпадает с вновь полученным, то алгоритм выходит из цикла. Сравнение массивом осуществляется методом array_equal(). Функция возвращает матрицу с восстановленным изображением. Кол-во нейронов в сети составляет 196 (size**2). Отношение числа образов к числу нейронов сети равняется 0,015 и не превышает 0,14.
Листинг 6 – Создание сети Хопфилда
class HopfieldNetwork:
def __init__(self, size):
self.size = size
self.weights = np.zeros((size **2, size **2)) # матрица весов
def train(self, patterns):
for pattern in patterns:
flat_pattern = pattern.flatten()
self.weights += np.outer(flat_pattern, flat_pattern.T) # получение весов
np.fill_diagonal(self.weights, 0) # обнуление диагонали
def predict(self, pattern, max_iterations=100): # обучение сети
flat_pattern = pattern.flatten()
for _ in range(max_iterations):
new_pattern = np.dot(self.weights, flat_pattern)
new_pattern[new_pattern >= 0] = 1
new_pattern[new_pattern < 0] = -1
if np.array_equal(new_pattern, flat_pattern):
return new_pattern.reshape((self.size, self.size))
flat_pattern = new_pattern
return flat_pattern.reshape((self.size, self.size))
Далее создается экземпляр класса определяющего НС. В качестве эталонных образов задан список содержащий квадрат, круг, треугольник. На основе этого списка выполняется обучение сети - настройка весов. Задается пустой список вариантов, для которых сеть не смогла восстановить фигуру. В методе test_on_figure() задаются пустые массивы для полученных предсказаний и уровня шума при них. Далее перебираются зашумленные образы, для каждого выполняется предсказание. Если изображение восстанавливается неверно (матрица предсказания не равна эталонному образу), то к списку проваленных предсказаний добавляется название фигуры, уровень шума, исходный и предсказанный образы. При помощи метода matshow() исходные и предсказанные образы визуализируются. Метод возвращает список предсказанных значений (по зашумленным квадратам, треугольникам и кругам) и степени их зашумления (Листинг 7).
