механизм внимания

искусственный интеллект

1. Механизм внимания

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

С точки зрения роли внимания мы можем классифицировать типы внимания с двух точек зрения: Пространственное внимание, временное внимание. Такая классификация больше относится к прикладному уровню, а от функции внимания ее можно разделить на мягкое внимание и жесткое внимание, о чем мы и говорили, векторное распределение вывода внимания является своего рода одним горячим. распределение также является мягким мягким распределением, которое напрямую влияет на выбор контекстной информации.

Зачем присоединяться Внимание:

Когда входная последовательность очень длинная, модели трудно изучить разумное векторное представление.

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

Структуру кодека нельзя объяснить, что делает невозможным его проектирование.

Основная идея механизма Attention состоит в том, чтобы сломать ограничение, заключающееся в том, что традиционная структура кодер-декодер полагается на внутренний вектор фиксированной длины при кодировании и декодировании. Механизм внимания реализуется путем сохранения промежуточных результатов вывода кодировщика LSTM во входной последовательности, а затем обучения модели выборочному изучению этих входных данных и связыванию с ними выходной последовательности при выводе модели.

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

Модель, основанная на внимании, на самом деле является мерой сходства.Текущий ввод примерно аналогичен целевому состоянию, поэтому вес текущего ввода будет больше. Это чтобы добавить внимание к оригинальной модели.

В частности, существует проблема с моделью LSTM/RNN, использующей традиционную структуру кодер-декодер: независимо от входной длины она кодируется в векторное представление фиксированной длины, из-за чего модель плохо обучается для длинных входных последовательностей (декодирование неэффективно). ). Механизм внимания преодолевает вышеупомянутые проблемы.Принцип заключается в том, чтобы выборочно сосредоточиться на соответствующей информации на входе, когда модель выводит. Методы, использующие механизм внимания, широко используются в различных задачах прогнозирования последовательности, включая перевод текста, распознавание речи и т. д.

2. Код

 import os

import re

import csv

import codecs

import numpy as np

import pandas as pd

from keras import backend as K

from keras.engine.topology import Layer

from keras import initializers, regularizers, constraints

np.random.seed(2018)

class Attention(Layer):

    def __init__(self,
                 W_regularizer=None, b_regularizer=None,
                 W_constraint=None, b_constraint=None,
                 bias=True, **kwargs):
        self.supports_masking = True
        # self.init = initializations.get('glorot_uniform')
        self.init = initializers.get('glorot_uniform')

        self.W_regularizer = regularizers.get(W_regularizer)
        self.b_regularizer = regularizers.get(b_regularizer)

        self.W_constraint = constraints.get(W_constraint)
        self.b_constraint = constraints.get(b_constraint)

        self.bias = bias

        self.features_dim = 0
        super(Attention, self).__init__(**kwargs)

    def build(self, input_shape):
        self.step_dim = input_shape[1]
        assert len(input_shape) == 3 # batch ,timestep , num_features
        print(input_shape)
        self.W = self.add_weight((input_shape[-1],), #num_features
                                 initializer=self.init,
                                 name='{}_W'.format(self.name),
                                 regularizer=self.W_regularizer,
                                 constraint=self.W_constraint)
        self.features_dim = input_shape[-1]

        if self.bias:
            self.b = self.add_weight((input_shape[1],),#timesteps
                                     initializer='zero',
                                     name='{}_b'.format(self.name),
                                     regularizer=self.b_regularizer,
                                     constraint=self.b_constraint)
        else:
            self.b = None

        self.built = True

    def compute_mask(self, input, input_mask=None):
        # do not pass the mask to the next layers
        return None

    def call(self, x, mask=None):
        features_dim = self.features_dim
        step_dim = self.step_dim
        print(K.reshape(x, (-1, features_dim)))# n, d
        print(K.reshape(self.W, (features_dim, 1)))# w= dx1
        print(K.dot(K.reshape(x, (-1, features_dim)), K.reshape(self.W, (features_dim, 1))))#nx1

        eij = K.reshape(K.dot(K.reshape(x, (-1, features_dim)), K.reshape(self.W, (features_dim, 1))), (-1, step_dim))#batch,step
        print(eij)
        if self.bias:
            eij += self.b

        eij = K.tanh(eij)

        a = K.exp(eij)

        # apply mask after the exp. will be re-normalized next
        if mask is not None:
            # Cast the mask to floatX to avoid float64 upcasting in theano
            a *= K.cast(mask, K.floatx())

        a /= K.cast(K.sum(a, axis=1, keepdims=True) + K.epsilon(), K.floatx())
        print(a)
        a = K.expand_dims(a)
        print("expand_dims:")
        print(a)
        print("x:")
        print(x)
        weighted_input = x * a
        print(weighted_input.shape)
        return K.sum(weighted_input, axis=1)

    def compute_output_shape(self, input_shape):
        # return input_shape[0], input_shape[-1]
        return input_shape[0], self.features_dim

3. Резюме

В общем, механизм внимания представляет собой механизм взвешенного суммирования, до тех пор, пока мы используем взвешенное суммирование, независимо от того, какое причудливое взвешивание или причудливое суммирование вы используете, до тех пор, пока вы вычисляете скрытое состояние на основе существующей информации Взвешенное и суммированное, то используется внимание, а так называемое самовнимание заключается только в взвешенном суммировании внутри предложения (в отличие от взвешенного суммирования скрытого состояния кодировщика декодером в seq2seq).

Лично я считаю, что внимание к себе имеет более широкий охват, а ключ-значение на самом деле является более широким определением внимания. Предыдущее внимание может быть покрыто вниманием с ключом-значением. Например, много раз мы ставили k и v. Все это считается одним и тем же. , а при выполнении self также может быть quey=key=value.