不确定我的自动编码器神经网络给我的 Keras 预测结果 [英] Unsure about the result my autoencoder neural network is giving me from Keras predict

查看:20
本文介绍了不确定我的自动编码器神经网络给我的 Keras 预测结果的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试构建一个自动编码器神经网络,用于在单列文本列表中查找异常值.我的输入有 138 行,它们看起来像这样:

I'm trying to build an Autoencoder neural network for finding outliers in a single column list of text. My input have 138 lines and they look like this:

amaze_header_2.png
amaze_header.png
circle_shape.xml
disableable_ic_edit_24dp.xml
fab_label_background.xml
fab_shadow_black.9.png
fab_shadow_dark.9.png

我使用 Keras 构建了一个自动编码器网络,并使用 python 函数将我的文本输入转换为一个数组,其中每个字符的 ascii 表示,用零填充,使它们都具有相同的大小.

I've built an autoencoder network using Keras, and I use a python function to convert my text input into an array with the ascii representation of each character, padded by zeroes so they all have the same size.

我的完整代码是这样的:

And my full code is like this:

import sys
from keras import Input, Model
import matplotlib.pyplot as plt
from keras.layers import Dense
import numpy as np
from pprint import pprint
from google.colab import drive

# Monta o arquivo do Google Drive
drive.mount('/content/drive')
with open('/content/drive/My Drive/Colab Notebooks/drawables.txt', 'r') as arquivo:
    dados = arquivo.read().splitlines()

# Define uma função para pegar uma lista e retornar um inteiro com o tamanho do 
# maior elemento
def tamanho_maior_elemento(lista):
  maior = 0
  for elemento in lista:
    tamanho_elemento = len(elemento)
    if tamanho_elemento > maior:
      maior = tamanho_elemento
  return maior

# Define uma função para pegar uma lista e o tamanho do maior elemento e
# retornar uma lista contendo uma outra lista com cada caractere convertido para
# ascii, antes de converter são adicionados zeros a direita para eles ficarem
# com o mesmo tamanho do maior elemento.
def texto_para_ascii(lista, tamanho_maior_elemento):
  #para cada linha
  lista_ascii = list()
  for elemento in lista:
    elemento_ascii_lista = list()
    #coloca zeros do lado da string
    elemento_com_zeros = elemento.ljust(tamanho_maior_elemento, "0")
    for caractere in elemento_com_zeros:
      elemento_ascii_lista.append(ord(caractere))
    lista_ascii.append(elemento_ascii_lista)
  return lista_ascii

def ascii_para_texto(lista):
  #para cada linha
  lista_ascii = list()
  for elemento in lista:
    elemento_ascii_lista = list()
    for caractere in elemento:
      elemento_ascii_lista.append(chr(caractere))
    elemento_ascii_string = "".join(elemento_ascii_lista)
    lista_ascii.append(elemento_ascii_string)
  return lista_ascii

# Pega o tamanho do maior elemento
tamanho_maior_elemento = tamanho_maior_elemento(dados)

# Pega o tamanho da lista
tamanho_lista = len(dados)

# Converte os dados para ascii
dados_ascii = texto_para_ascii(dados, tamanho_maior_elemento)

# Converte a linha de dados em ascii para um array numpy
np_dados_ascii = np.array(dados_ascii)

# Define o tamanho da camada comprimida
tamanho_comprimido = int(tamanho_maior_elemento/5)

# Cria a camada de Input com o tamanho do maior elemento
dados_input = Input(shape=(tamanho_maior_elemento,))

# Cria uma camada escondida com o tamanho da camada comprimida
hidden = Dense(tamanho_comprimido, activation='relu')(dados_input)

# Cria a camada de saida com o tamanho do maior elemento
output = Dense(tamanho_maior_elemento, activation='relu')(hidden)
#resultado = Dense(tamanho_maior_elemento, activation='sigmoid')(output)
resultado = Dense(tamanho_maior_elemento)(output)

# Cria o modelo
autoencoder = Model(input=dados_input, output=resultado)

# Compila o modelo
autoencoder.compile(optimizer='adam', loss='mse')

# Faz o fit com os dados
history = autoencoder.fit(np_dados_ascii, np_dados_ascii, epochs=10)

# Plota o gráfico das epochs
plt.plot(history.history["loss"])
plt.ylabel("Loss")
plt.xlabel("Epoch")
plt.show()

# Pega a saída do predict
predict = autoencoder.predict(np_dados_ascii)

# Pega os índices do array que foram classificados
indices = np.argmax(predict, axis=0)

# Converte a saída do predict de array numpy para array normal
indices_list = indices.tolist()

identificados = list()
for indice in indices_list:
  identificados.append(dados[indice])

pprint(identificados)

我的 np.argmax(predict,axis=0) 函数返回一个数字列表,其中没有一个大于我的数组大小,所以我假设它们是我输入中的位置异常值的数组.

My np.argmax(predict, axis=0) function returns a list of numbers, which none of them are higher than my array size, so I presumed that they are the positions in my input array that were outliers.

但我非常不确定如何解释预测数据,我的指数"变量如下所示:

But I'm super unsure on how to interpret the predict data, my "indices" variable looks like this:

array([116, 116,  74,  74,  97, 115,  34, 116,  39,  39, 116, 116, 115,
       116,  34,  74,  74,  34, 115, 116, 115,  74, 116,  39,  84, 116,
        39,  34,  34,  84, 115, 115,  34,  39,  34, 116, 116,  10])

我的解释是否正确?我的意思是,这些返回的数字是什么?它们看起来一点也不像我的输入.所以我假设它们是我输入数据数组上的位置.我说得对吗?

Have I done the correct interpretation? I mean, what are these numbers being returned? They look nothing like my input. So I assumed that they are the positions on my input data array. Am I right?

如果在脚本结束时我这样做:

if at the end of the script I do:

print("--------------")
pprint(np_dados_ascii)
print("--------------")
pprint(predict)

我得到以下数据:

--------------
array([[ 97,  98, 111, ...,  48,  48,  48],
       [ 97, 109,  97, ...,  48,  48,  48],
       [ 97, 109,  97, ...,  48,  48,  48],
       ...,
       [115,  97, 102, ...,  48,  48,  48],
       [115, 100,  95, ...,  48,  48,  48],
       [115, 101,  97, ...,  48,  48,  48]])
--------------
array([[86.44533 , 80.48006 , 13.409852, ..., 60.649754, 21.34232 ,
        24.23074 ],
       [98.18514 , 87.98954 , 14.873579, ..., 65.382866, 22.747816,
        23.74556 ],
       [85.682945, 79.46511 , 13.117042, ..., 60.182964, 21.096725,
        22.625275],
       ...,
       [86.989494, 77.36661 , 14.291222, ..., 53.586407, 18.540628,
        26.212025],
       [76.0646  , 70.029236, 11.804929, ..., 52.506832, 18.65119 ,
        21.961123],
       [93.25003 , 82.855354, 15.329873, ..., 56.992035, 19.869513,
        28.3672  ]], dtype=float32)

预测输出是什么意思?如果我的输入是整数数组,我不明白为什么会返回浮点数.

What do the predict output mean? I don't get why there are floats being returned if my input is an integer array.

它不应该是一个只包含异常值的 ascii 文本的具有不同形状的数组(在我的结果中,它们是相等的)?

Shouldn't it be an array with a different shape (in my result, they are equal) containing just the ascii text of the outliers?

推荐答案

自动编码器是一种神经网络,用于将高维输入映射到低维表示.自编码器的架构很容易理解和实现.

Autoencoders are a type of NN used to map higher dimensional input to a lower dimensional representation. The architecture of an autoencoder is quite easy to understand and implement.

这篇文章以简单的方式解释了它们的作用以及您应该如何解释您的数据.

This article explains in a simple way what they do and how you should interpret your data.

对于您的具体情况,首先,我会尝试不同的输入表示形式,在任何_"或."之后拆分每个单词.并使用 Keras 嵌入层将其编码为向量:here a tutorial关于如何使用嵌入层

For your specific case, first of all, I would try a different representation of the input, splitting each word after any '_' or '.' and encode it as a vector using the Keras Embedding layer: here a tutorial on how to use Embedding Layers

然后,您真正想要的是查看中间隐藏层的输出,也就是将输入编码到低维空间的输出.从这个较低维度的空间中,您可以训练分类器来检测异常值(如果您有地面实况),或者使用其他无监督学习技术来执行异常检测或简单地进行可视化和聚类.

Then, what you really want is to look at the output of your middle hidden layer, that is the one that encodes your input into a lower dimensional space. From this lower dimensional space, you can then either train a classifier to detect outliers if you have ground truth or use other unsupervised learning techniques to perform anomaly detection or simply visualization and clustering.

这篇关于不确定我的自动编码器神经网络给我的 Keras 预测结果的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆