Ir para o conteúdo

5. Multi-Layer Perceptron

Apresentação: Perceptrons Multi-Camada (MLPs)

Todo neurônio faz sempre as mesmas duas coisas: uma soma ponderada de tudo o que chega até ele (mais um bias) e a passagem dessa soma por uma ativação não-linear. O painel de ampliação acima mostra essas duas operações; a rede é esse mesmo neurônio repetido e empilhado.

\[ y_k = \sigma \left( \sum_{j=1}^{m} v_{kj} \, \sigma \left( \sum_{i=1}^{n} w_{ji} x_i + b^{h}_{j} \right) + b^{y}_{k} \right) \]

onde:

  • \(y_k\) é a saída para o \(k\)-ésimo neurônio de saída.
  • \(x_i\) são as features de entrada.
  • \(w_{ji}\) é o peso que conecta a \(i\)-ésima entrada ao \(j\)-ésimo neurônio oculto — o neurônio que recebe vem primeiro, de modo que \(w_{ji}\) é a entrada da linha \(j\), coluna \(i\) de \(\mathbf{W}\).
  • \(v_{kj}\) é o peso que conecta o \(j\)-ésimo neurônio oculto ao \(k\)-ésimo neurônio de saída.
  • \(b^{h}_{j}\) é o bias para o \(j\)-ésimo neurônio oculto.
  • \(b^{y}_{k}\) é o bias para o \(k\)-ésimo neurônio de saída.
  • \(m\) é o número de neurônios ocultos.
  • \(n\) é o número de features de entrada.
  • \(\sigma\) é a função de ativação aplicada às somas ponderadas em cada camada, como sigmoid, tanh ou ReLU.

Representação matricial da arquitetura MLP:

\[ \begin{align*} \text{Camada de Entrada:} & \quad \mathbf{x} = [x_1, x_2, \ldots, x_n]^T \\ \text{Camada Oculta:} & \quad \mathbf{h} = \sigma (\mathbf{W} \mathbf{x} + \mathbf{b}^h) \\ \text{Camada de Saída:} & \quad \mathbf{y} = \sigma (\mathbf{V} \mathbf{h} + \mathbf{b}^y) \end{align*} \]

Funções de Ativação

Sigmoid Tanh ReLU
\(\sigma(x) = \displaystyle \frac{1}{1 + e^{-x}}\) \(\tanh(x) = \displaystyle \frac{e^{2x} - 1}{e^{2x} + 1}\) \(\text{ReLU}(x) = \max(0, x)\)
\(\sigma'(x) = \sigma(x)(1 - \sigma(x))\) \(\tanh'(x) = 1 - \tanh^2(x)\) \(\text{ReLU}'(x) = \begin{cases} 1 & \text{se } x > 0 \\ 0 & \text{se } x \leq 0 \end{cases}\)
Sigmoid é uma curva S suave que produz valores entre 0 e 1, sendo adequada para classificação binária. Tanh é uma curva suave que produz valores entre -1 e 1, centralizando os dados em zero, o que pode ajudar na convergência. ReLU é uma função linear por partes que produz zero para entradas negativas e a própria entrada para positivas, permitindo treinamento mais rápido e reduzindo o gradiente desvanecente.

Os três compartilham o mesmo eixo horizontal, então as derivadas tracejadas podem ser comparadas diretamente. Repare de onde vem o problema do gradiente desvanecente: a derivada da sigmoid nunca passa de 0,25, de modo que cada camada atravessada pelo gradiente o encolhe pelo menos quatro vezes, enquanto a derivada da ReLU vale exatamente 1 onde a unidade está ativa.

O que uma camada oculta já consegue

Com uma ativação não-linear, uma camada oculta já basta em princípio. O teorema da aproximação universal (Cybenko, 1989, para a sigmoid; Hornik, 1991, para qualquer ativação limitada e não constante) diz que um MLP com uma única camada oculta aproxima qualquer função contínua numa região limitada tão bem quanto se queira, desde que tenha neurônios ocultos suficientes. Ele não diz quantos neurônios isso exige nem se o gradiente descendente vai encontrar os pesos — essas são as perguntas do capítulo de Deep Learning. Sem a ativação o teorema cai: duas camadas lineares se compõem numa só, \(\mathbf{V}(\mathbf{W}\mathbf{x}) = (\mathbf{V}\mathbf{W})\mathbf{x}\).

A retropropagação é o algoritmo usado para treinar MLPs ajustando pesos e biases com base no erro entre a saída prevista e o alvo real. O processo envolve três passos principais:

  1. Passagem Direta: Os dados de entrada passam pela rede, camada por camada, para calcular a saída.
  2. Cálculo da Perda: Calcula-se a perda entre a saída prevista e o alvo real usando uma função de perda, como erro quadrático médio ou cross-entropy.
  3. Passagem Reversa: O erro é propagado de volta pela rede para calcular os gradientes da perda em relação a cada peso e bias. Esses gradientes são usados para atualizar os pesos e biases usando um algoritmo de otimização, como o gradiente descendente estocástico (SGD) ou o Adam.

Passagem Direta (Feedforward)

Considere um MLP com:

  • 2 neurônios de entrada: \(x_1\) e \(x_2\)
  • 1 camada oculta com 2 neurônios: \(h_1\) e \(h_2\)
  • 1 neurônio de saída: \(y\)

Assumimos funções de ativação sigmoid para as camadas oculta e de saída:

\[\displaystyle \sigma(z) = \frac{1}{1 + e^{-z}}\]

com derivada

\[\sigma'(z) = \sigma(z)(1 - \sigma(z))\]

A arquitetura e a passagem direta por ela podem ser percorridas passo a passo. Os valores mostrados são os mesmos da Simulação Numérica mais adiante, de modo que o diagrama e a aritmética são o mesmo exemplo:

Em termos matemáticos, o processo de passagem direta é descrito como:

\[ \begin{align*} \text{Camada de Entrada:} & \quad \mathbf{x} = [x_1, x_2]^T \\ \text{Camada Oculta:} & \quad \mathbf{h} = \sigma (\mathbf{W} \mathbf{x} + \mathbf{b}^h) \\ \text{Camada de Saída:} & \quad \mathbf{y} = \sigma (\mathbf{V} \mathbf{h} + \mathbf{b}^y) \end{align*} \]

ou, de forma mais canônica para o nosso MLP simples:

\[ \hat{y} = \sigma \left( \underbrace{v_{11} \underbrace{\sigma \left( \underbrace{w_{11} x_1 + w_{12} x_2 + b^h_1}_{z_1} \right)}_{h_1} + v_{12} \underbrace{\sigma \left( \underbrace{w_{21} x_1 + w_{22} x_2 + b^h_2}_{z_2} \right)}_{h_2} + b^y_1 }_{u} \right) \]
  1. Pré-ativação da camada oculta:
\[ \begin{align} z_1 & = w_{11} x_1 + w_{12} x_2 + b^h_1 \\ z_2 & = w_{21} x_1 + w_{22} x_2 + b^h_2 \end{align} \]
  1. Ativações da camada oculta:
\[ \begin{align} h_1 & = \sigma(z_1) \\ h_2 & = \sigma(z_2) \end{align} \]
  1. Pré-ativação da camada de saída:
\[ \begin{align} u & = v_{11} h_1 + v_{12} h_2 + b^y_1 \end{align} \]
  1. Ativação da camada de saída:
\[ \begin{align} \hat{y} & = \sigma(u) \end{align} \]

onde \(\sigma\) é a função de ativação, \(w_{ji}\) é o peso da entrada \(i\) para o neurônio oculto \(j\) e \(v_{kj}\) é o peso do neurônio oculto \(j\) para o neurônio de saída \(k\) — o neurônio que recebe vem primeiro, como nas linhas de \(\mathbf{W}\) e \(\mathbf{V}\). Os biases \(b^h_1\), \(b^h_2\) e \(b^y_1\) são somados nas respectivas camadas. \(\hat{y}\) é a saída prevista pelo MLP.

Cálculo da Perda

A função de perda quantifica a diferença entre a saída prevista e o alvo real. Para tarefas de regressão, o Erro Quadrático Médio (MSE) é comum:

\[ L = \text{MSE} = \frac{1}{N} \sum_{i=1}^{N} (y_i - \hat{y}_i)^2 \]

onde \(N\) é o número de amostras, \(y_i\) é a saída verdadeira e \(\hat{y}_i\) é a saída prevista.

Retropropagação: Calculando Gradientes

O algoritmo de retropropagação é um método para treinar MLPs minimizando o erro entre a saída prevista e o alvo real. Ele envolve dois passos principais: a passagem direta e a passagem reversa. A atualização de pesos e biases usa os gradientes calculados na passagem reversa.

A retropropagação calcula as derivadas parciais de \(L\) em relação a cada parâmetro usando a regra da cadeia, partindo da saída e propagando os erros de volta.

Regra de Atualização

Para atualizar os parâmetros durante o treino (por exemplo, com gradiente descendente e taxa de aprendizado \(\eta\)), para cada peso ou bias \(p\):

\[ p \leftarrow p - \eta \cdot \frac{\partial L}{\partial p} \]

Esta derivação supõe um único exemplo; para batches, tira-se a média dos gradientes. Para outras ativações ou perdas (por exemplo, softmax com cross-entropy) os deltas mudam de acordo, mas a estrutura da regra da cadeia continua parecida.

Os cinco passos abaixo são o mesmo percurso que o diagrama faz. A rede é a da passagem direta, com os valores que ela produziu ainda sobre os neurônios — a retropropagação não os recalcula, ela os reaproveita:

Passo 1: Erro da Camada de Saída

O termo de erro (delta) da saída, escrito \(\delta\) para não ser confundido com a ativação \(\sigma\), é:

\[ \begin{align} \delta_y = \frac{\partial L}{\partial u} &= \overbrace{\frac{\partial L}{\partial \hat{y}} \cdot \frac{\partial \hat{y}}{\partial u}}^{\text{regra da cadeia}} \\ &= \overbrace{\frac{2}{N}(\hat{y} - y)}^{\text{MSE}} \cdot \overbrace{\sigma'(u)}^{\text{sigmoid}} \\ \\ &= \frac{2}{N}(\hat{y} - y) \cdot \hat{y}(1 - \hat{y}) \end{align} \]

Passo 2: Gradientes para Pesos e Bias de Saída

Lembre

\[ \begin{align} u & = v_{11} h_1 + v_{12} h_2 + b^y_1 \end{align} \]

Usando \(\delta_y\):

\(\begin{align} \frac{\partial L}{\partial v_{11}} &= \delta_y \cdot h_1 \\ \\ \overbrace{\frac{\partial L}{\partial u} \cdot \frac{\partial u}{\partial v_{11}}}^{\text{regra da cadeia}} &= \delta_y \cdot h_1 \end{align}\)

Da mesma forma:

\(\begin{align} \frac{\partial L}{\partial v_{12}} &= \delta_y \cdot h_2 \\ \\ \overbrace{\frac{\partial L}{\partial u} \cdot \frac{\partial u}{\partial v_{12}}}^{\text{regra da cadeia}} &= \delta_y \cdot h_2 \end{align}\)

Para o bias:

\(\begin{align} \frac{\partial L}{\partial b^y_1} &= \delta_y \cdot 1 \\ \\ \overbrace{\frac{\partial L}{\partial u} \cdot \frac{\partial u}{\partial b^y_1}}^{\text{regra da cadeia}} &= \delta_y \end{align}\)

Passo 3: Erros da Camada Oculta

Lembre

\[ \begin{align} z_1 & = w_{11} x_1 + w_{12} x_2 + b^h_1 \\ z_2 & = w_{21} x_1 + w_{22} x_2 + b^h_2 \end{align} \]

Propague o erro de volta para a camada oculta. Para cada neurônio oculto:

\(\begin{array}{rll} \displaystyle \delta_{h_1} &= \displaystyle \frac{\partial L}{\partial z_1} \\ &= \displaystyle \frac{\partial L}{\partial h_1} & \displaystyle \cdot \frac{\partial h_1}{\partial z_1} \\ &= \displaystyle \overbrace{ \left( \frac{\partial L}{\partial u} \cdot \frac{\partial u}{\partial h_1} \right)}^{\text{regra da cadeia}} & \cdot \sigma'(z_1) \\ &= (\delta_y \cdot v_{11}) & \cdot \sigma'(z_1) \\ &= (\delta_y \cdot v_{11}) & \cdot h_1(1 - h_1) \end{array}\)

Da mesma forma:

\(\delta_{h_2} = (\delta_y \cdot v_{12}) \cdot h_2(1 - h_2)\)

Passo 4: Gradientes para Pesos e Biases Ocultos

Usando os deltas ocultos:

\(\begin{align} \frac{\partial L}{\partial w_{11}} &= \frac{\partial L}{\partial z_1} \cdot \frac{\partial z_1}{\partial w_{11}} &= \delta_{h_1} \cdot x_1 \end{align}\)

\(\begin{align} \frac{\partial L}{\partial w_{12}} &= \frac{\partial L}{\partial z_1} \cdot \frac{\partial z_1}{\partial w_{12}} &= \delta_{h_1} \cdot x_2 \end{align}\)

\(\begin{align} \frac{\partial L}{\partial w_{21}} &= \frac{\partial L}{\partial z_2} \cdot \frac{\partial z_2}{\partial w_{21}} &= \delta_{h_2} \cdot x_1 \end{align}\)

\(\begin{align} \frac{\partial L}{\partial w_{22}} &= \frac{\partial L}{\partial z_2} \cdot \frac{\partial z_2}{\partial w_{22}} &= \delta_{h_2} \cdot x_2 \end{align}\)

e da mesma forma para os biases:

\(\begin{align} \frac{\partial L}{\partial b^h_1} &= \delta_{h_1} \cdot 1 &= \delta_{h_1} \end{align}\)

\(\begin{align} \frac{\partial L}{\partial b^h_2} &= \delta_{h_2} \cdot 1 &= \delta_{h_2} \end{align}\)

Passo 5: Atualizar Pesos e Biases

Lembre

\[ p \leftarrow p - \eta \cdot \frac{\partial L}{\partial p} \]

Por fim, atualize os pesos e biases usando os gradientes calculados e uma taxa de aprendizado \(\eta\):

\(\begin{align} v_{11} & \leftarrow v_{11} - \eta \cdot \frac{\partial L}{\partial v_{11}} \\ v_{12} & \leftarrow v_{12} - \eta \cdot \frac{\partial L}{\partial v_{12}} \\ \\ w_{11} & \leftarrow w_{11} - \eta \cdot \frac{\partial L}{\partial w_{11}} \\ w_{12} & \leftarrow w_{12} - \eta \cdot \frac{\partial L}{\partial w_{12}} \\ w_{21} & \leftarrow w_{21} - \eta \cdot \frac{\partial L}{\partial w_{21}} \\ w_{22} & \leftarrow w_{22} - \eta \cdot \frac{\partial L}{\partial w_{22}} \\ \\ b^h_1 & \leftarrow b^h_1 - \eta \cdot \frac{\partial L}{\partial b^h_1} \\ b^h_2 & \leftarrow b^h_2 - \eta \cdot \frac{\partial L}{\partial b^h_2} \\ \\ b^y_1 & \leftarrow b^y_1 - \eta \cdot \frac{\partial L}{\partial b^y_1} \end{align}\)


Simulação Numérica

Com base na arquitetura MLP e nos passos de retropropagação descritos acima, podemos rodar uma simulação numérica simples para demonstrar o treinamento de um MLP por retropropagação.

Inicialização

As matrizes de pesos e os vetores de bias são inicializados assim (valores pequenos em \([0,1]\), escolhidos à mão para que a conta seja fácil de acompanhar; na prática eles são sorteados):

\[ \mathbf{W} = \begin{bmatrix} 0.2 & 0.4 \\ 0.6 & 0.8 \end{bmatrix}, \quad \mathbf{b}^h = [0.1, 0.2]^T \]
\[ \mathbf{V} = \begin{bmatrix} 0.3 & 0.5 \end{bmatrix}, \quad b^y = 0.4 \]
\[ \eta = 0.7 \]

Passagem Direta

Para a amostra:

\[ \mathbf{x} = \begin{bmatrix} 0.5 \\ 0.8 \end{bmatrix}, \quad y = 0 \]
  1. Calcule a pré-ativação da camada oculta:

    \[ \begin{array}{ll} \mathbf{z} &= \mathbf{W} \mathbf{x} + \mathbf{b}^h \\ &= \begin{bmatrix} 0.2 & 0.4 \\ 0.6 & 0.8 \end{bmatrix} \begin{bmatrix} 0.5 \\ 0.8 \end{bmatrix} + \begin{bmatrix} 0.1 \\ 0.2 \end{bmatrix} \\ &= \begin{bmatrix} 0.2*0.5 + 0.4*0.8 + 0.1 \\ 0.6*0.5 + 0.8*0.8 + 0.2 \end{bmatrix} \\ \mathbf{z} &= \begin{bmatrix} 0.52 \\ 1.14 \end{bmatrix} \end{array} \]
  2. Calcule as ativações da camada oculta:

    \[ \begin{array}{ll} \mathbf{h} &= \sigma(\mathbf{z}) \\ &= \sigma \left( \begin{bmatrix} 0.52 \\ 1.14 \end{bmatrix} \right) \\ &= \begin{bmatrix} \displaystyle \frac{1}{1 + e^{-0.52}} \\ \displaystyle \frac{1}{1 + e^{-1.14}} \end{bmatrix} \\ \mathbf{h} &\approx \begin{bmatrix} 0.627 \\ 0.758 \end{bmatrix} \end{array} \]
  3. Calcule a pré-ativação da camada de saída:

    \[ \begin{array}{ll} u &= \mathbf{V} \mathbf{h} + b^y \\ &= \begin{bmatrix} 0.3 & 0.5 \end{bmatrix} \begin{bmatrix} 0.627 \\ 0.758 \end{bmatrix} + 0.4 \\ &= 0.3*0.627 + 0.5*0.758 + 0.4 \\ u &\approx 0.967 \end{array} \]
  4. Calcule a ativação da camada de saída:

    \[ \begin{array}{ll} \hat{y} &= \sigma(u) \\ &= \sigma(0.967) \\ &= \displaystyle \frac{1}{1 + e^{-0.967}} \\ \hat{y} &\approx 0.725 \end{array} \]

Cálculo da Perda

Usando o Erro Quadrático Médio (MSE):

\[ \begin{array}{ll} \text{MSE} =& L &= \displaystyle \frac{1}{N} \sum_{i=1}^{N} (y_i - \hat{y}_i)^2 \\ & L &= \displaystyle \frac{1}{1} (y - \hat{y})^2 \\ & L &\approx (0 - 0.725)^2 \\ & L &\approx 0.5249 \end{array} \]

Passagem Reversa

  1. Calcule os gradientes da camada de saída:

    \[ \begin{array}{ll} \displaystyle \delta_y = \frac{\partial L}{\partial u} &= \displaystyle \frac{\partial L}{\partial \hat{y}} \cdot \frac{\partial \hat{y}}{\partial u} \\ &= 2(\hat{y} - y) \cdot \underbrace{\hat{y} (1 - \hat{y})}_{\sigma'(u)} \\ &\approx 2(0.725 - 0) \cdot 0.725 \cdot (1 - 0.725) \\ &\approx 0.289 \end{array} \]

    O gradiente é positivo: aumentar \(u\) aumentaria a perda, então a atualização abaixo o diminui — e é isso que empurra \(\hat{y}\) na direção do alvo \(y = 0\).

  2. Calcule os gradientes da camada oculta:

    \[ \begin{array}{ll} \boldsymbol{\delta}_h &= \displaystyle \frac{\partial L}{\partial \mathbf{z}} = \underbrace{\left( \delta_y \, \mathbf{V}^T \right)}_{\text{volta por } \mathbf{V}} \odot \underbrace{\mathbf{h} \odot (1 - \mathbf{h})}_{\sigma'(\mathbf{z})} \\ &\approx 0.289 \cdot \begin{bmatrix} 0.3 \\ 0.5 \end{bmatrix} \odot \begin{bmatrix} 0.627 \\ 0.758 \end{bmatrix} \odot \begin{bmatrix} 0.373 \\ 0.242 \end{bmatrix} \\ &\approx \begin{bmatrix} 0.087 \\ 0.145 \end{bmatrix} \odot \begin{bmatrix} 0.234 \\ 0.184 \end{bmatrix} \\ &\approx \begin{bmatrix} 0.020 \\ 0.027 \end{bmatrix} \end{array} \]

    onde \(\odot\) é o produto elemento a elemento.

  3. Calcule os gradientes dos pesos — o produto externo dos deltas com a entrada da camada:

    \[ \begin{array}{ll} \displaystyle \frac{\partial L}{\partial \mathbf{W}} &= \boldsymbol{\delta}_h \, \mathbf{x}^T \\ &\approx \begin{bmatrix} 0.020 \\ 0.027 \end{bmatrix} \begin{bmatrix} 0.5 & 0.8 \end{bmatrix} \\ &\approx \begin{bmatrix} 0.010 & 0.016 \\ 0.013 & 0.021 \end{bmatrix} \end{array} \]
    \[ \begin{array}{ll} \displaystyle \frac{\partial L}{\partial \mathbf{V}} &= \delta_y \, \mathbf{h}^T \\ &\approx 0.289 \cdot \begin{bmatrix} 0.627 & 0.758 \end{bmatrix} \\ &\approx \begin{bmatrix} 0.181 & 0.219 \end{bmatrix} \end{array} \]
  4. Calcule os gradientes dos biases — um bias sempre vê uma entrada igual a 1, então o gradiente dele é o próprio delta:

    \[ \frac{\partial L}{\partial b^y} = \delta_y \approx 0.289, \qquad \frac{\partial L}{\partial \mathbf{b}^h} = \boldsymbol{\delta}_h \approx \begin{bmatrix} 0.020 \\ 0.027 \end{bmatrix} \]
  5. Atualize os parâmetros:

    \[ \begin{array}{ll} \mathbf{W} &\leftarrow \mathbf{W} - \eta \displaystyle \frac{\partial L}{\partial \mathbf{W}} \\ &\leftarrow \displaystyle \begin{bmatrix} 0.2 & 0.4 \\ 0.6 & 0.8 \end{bmatrix} - 0.7 \cdot \displaystyle \begin{bmatrix} 0.010 & 0.016 \\ 0.013 & 0.021 \end{bmatrix} \\ &\leftarrow \begin{bmatrix} 0.193 & 0.389 \\ 0.591 & 0.785 \end{bmatrix} \\ \mathbf{V} &\leftarrow \mathbf{V} - \eta \displaystyle \frac{\partial L}{\partial \mathbf{V}} \\ &\leftarrow \displaystyle \begin{bmatrix} 0.3 & 0.5 \end{bmatrix} - 0.7 \cdot \displaystyle \begin{bmatrix} 0.181 & 0.219 \end{bmatrix} \\ &\leftarrow \begin{bmatrix} 0.173 & 0.347 \end{bmatrix}\\ \\ b^y &\leftarrow b^y - \eta \displaystyle \frac{\partial L}{\partial b^y} \\ &\leftarrow 0.4 - 0.7 \cdot 0.289 \\ &\leftarrow 0.198 \\ \mathbf{b}^h &\leftarrow \mathbf{b}^h - \eta \displaystyle \frac{\partial L}{\partial \mathbf{b}^h} \\ &\leftarrow \begin{bmatrix} 0.1 \\ 0.2 \end{bmatrix} - 0.7 \cdot \begin{bmatrix} 0.020 \\ 0.027 \end{bmatrix} \\ &\leftarrow \begin{bmatrix} 0.086 \\ 0.181 \end{bmatrix} \end{array} \]

    Apresentando a mesma amostra à rede atualizada, \(\hat{y} \approx 0.638\) e \(L \approx 0.407\), contra \(0.525\) antes — um passo de gradiente descendente fez o que prometia.

  6. Repita o processo de treinamento para cada amostra ou por várias épocas. Há duas abordagens principais para o treinamento, o aprendizado online e o aprendizado em batch:

    • Aprendizado online é um método de treinar MLPs em que o modelo é atualizado após cada exemplo de treinamento. Essa abordagem permite convergência mais rápida e pode ser mais eficaz com conjuntos de dados grandes ou quando os dados não são estacionários.

    • Aprendizado em batch, por outro lado, atualiza o modelo depois de processar um batch de exemplos de treinamento. Esse método tende a dar atualizações mais estáveis e é o mais usado na prática, por aproveitar melhor os recursos computacionais.

O mesmo passo, interativo

O painel abaixo é essa mesma rede, com esses mesmos pesos e essa mesma amostra. Aperte um passo e a primeira linha de \(\mathbf{W}\) vira exatamente \([0{,}193;\ 0{,}389]\), o número calculado acima.

A espessura de cada aresta é \(|\partial L / \partial w|\). A comparação entre as duas camadas é o ponto: as ligações da saída são grossas, as da camada oculta são finas. O gradiente oculto é o da saída multiplicado por um peso e pela derivada da sigmoid — aqui, 0,23 e 0,18 — e é o encolhimento que a seção das ativações previu, agora medido em uma rede de duas camadas.

Duas coisas para experimentar:

  1. Suba o η com uma amostra só. A perda cai mais rápido e nunca sobe, por mais alto que ele vá. A saída é uma sigmoid: um passo exagerado satura em vez de passar do ponto.
  2. Ligue a segunda amostra, de alvo oposto; depois suba o η. Agora os dois gradientes se somam pedindo coisas diferentes e, a partir de \(\eta \approx 12\), a perda passa a subir e descer em vez de cair. É a instabilidade que a taxa de aprendizado controla, em quatro pesos.

Recursos Adicionais

Para uma compreensão mais intuitiva de redes neurais, recomendo a série de vídeos do 3Blue1Brown, que traz excelentes explicações visuais dos conceitos: https://www.3blue1brown.com/lessons/neural-networks

Para um tratamento mais completo de MLPs e retropropagação, veja os livros de Haykin1, Bishop2 e Goodfellow, Bengio e Courville3; para a teoria, a série Physics of Neural Networks4; para a otimização por trás da regra de atualização, as notas de Ghosh5.

Simulador: TensorFlow Playground

Um MLP pequeno treinado ao vivo no navegador, feito por Daniel Smilkov e Shan Carter no Google: escolha um conjunto de dados 2-D, o número de camadas ocultas e de neurônios, a ativação e a taxa de aprendizado; depois acompanhe a saída de cada neurônio e a fronteira de decisão mudarem a cada passo.

Abrir o TensorFlow Playground


Interativo: Visualizador de Passagem Direta do MLP

Observe as ativações se propagando por uma rede 2-entradas → 3-ocultos → 2-saídas. Ajuste os sliders de entrada e veja os valores fluírem camada por camada.

Entrada x₁
Entrada x₂
Ativação


  1. Haykin, S. (1999). Neural Networks: A Comprehensive Foundation (2nd ed.). Prentice Hall.  ↩

  2. Bishop, C. M. (2006). Pattern Recognition and Machine Learning. Springer.  ↩

  3. Goodfellow, I., Bengio, Y., & Courville, A. (2016). Deep Learning. MIT Press.  ↩

  4. Physics of Neural Networks, série de livros. ↩

  5. Introduction to Mathematical Optimization, de Indrajit Ghosh. ↩