爨 莹,吴 越
(西安石油大学 计算机学院,陕西 西安 710065)
时间序列数据是生活中常见的一种数据,在时间顺序上具有一定规律,且大量存在于金融贸易、工业生产、环境保护、网络安全等众多领域。时间序列异常检测在生产和生活中有着重要的作用,如在网络安全领域中分析网络异常行为,在金融领域中识别欺诈交易等。
传统时间序列异常检测方法(统计学方法或聚类方法),如高斯模型、ARIMA、K⁃means、IForest 等都属于统计机器学习的范畴。这些方法基本在每个时刻训练模型以预测下一时刻,若观测点与预测值相差太远,则将该点视为异常。这类方法的不足之处在于忽视了时间序列数据的序列特性,无法挖掘序列中的异常序列模式。本文提出基于Seq2Seq 深度自编码器的时间序列异常检测方法,使用Bi⁃LSTM 网络作为自编码器对输入序列进行编码压缩和解码重建,此方法能够更好地挖掘时序数据中的异常序列模式。
深度自编码器(Deep Autoencoder,DAE)是一种无监督或自监督算法,其本质是一种数据压缩算法。构建一个深度自编码器需要两个部分:编码器(Encoder)和解码器(Decoder)。编码器将输入压缩为潜在空间表征,解码器将潜在空间表征重建为输出,编码器和解码器都是神经网络。编码和解码方法都是由模型自动学习输入数据得到的,深度自编码器的结构如图1所示。
图1 深度自编码器结构
深度自编码器主要有以下三个特点:
1)数据相关性。自编码器只能编码与之前类似的数据。
2)数据有损性。自编码器解码得到的输出与原始输入相比会有信息损失。
3)自动学习性。自动编码器从数据中自动学习编码和解码的方法。
长短期记忆(Long Short⁃Term Memory,LSTM)网络是为解决循环神经网络(Recurrent Neural Networks,RNN)中梯度消失的问题提出的一种网络结构。LSTM单元可以处理长度可变的序列,并捕获其中的长期依赖性和非线性关系,已成为处理序列数据的标准方法。根据LSTM 单元提出的自学习门控方法,能确定LSTM单元是否记忆之前的状态或是否存储当前数据中的信息。LSTM 单元内部运算过程如图2 所示。
图2 LSTM 单元内部运算过程图
设时的输入序列为向量x,输出为h,LSTM 单元内部计算过程如下:
式中:c是时记忆单元中的状态向量;c是-1 时记忆单元中的状态向量;,和是参数矩阵和偏差向量;“⊙”表示元素积运算。此外,f表示遗忘门(Forget Gate),其作用是存储旧信息的权重向量;i表示输入门(Input Gate),用于获取新信息的权重向量;o示输出门(Output Gate),用于输出待输出的候选向量。在激活函数中,σ表示sigmoid 函数;σ和σ表示tanh 函数。
双向长短期记忆(Bi⁃directional Long Short⁃Term Memory,Bi⁃LSTM)网络通过引入第二层LSTM 单元来扩展单向LSTM 网络,其可以在前后两个方向上同时处理输入序列。在第二层中,隐含层单元的序列顺序相反,因此该网络可以同时利用过去和未来的序列信息。Bi⁃LSTM 网络结构图如图3 所示。
图3 Bi⁃LSTM 网络结构图
Seq2Seq 模型属于自编码器结构中的一类,常用于文本翻译、语音生成等自然语言处理领域。基本思想是用编码器将输入序列压缩成指定长度的向量,再用解码器将编码向量解码成指定长度的序列。
针对时间序列异常检测而言,假设样本中异常序列数量相对于正常序列来说是极少数的。在使用深度自动编码器的情况下,训练模型以学习正常时间序列中的序列模式。那么当时间序列输入深度自编码器中时,对于多数正常序列,模型可以很容易地发现并记住其中的序列模式,其重建误差相对可能较小;反之对于少数异常序列,模型很难对其序列模式进行挖掘,则重建误差相对可能较大。
因此对于输入的时间序列,若经过模型编码重建后与原始序列差异较大的话,则可以认为当前序列中可能存在异常,并可以进一步发现异常数据点。基于Seq2Seq 深度自编码器的时间序列异常检测模型,使用Bi⁃LSTM 网络作为自编码器对输入序列进行编码和重建。通过计算重建序列与原始序列之间的重建误差,并设置重建异常比率以获取误差阈值,将重建误差大于阈值的序列视为异常序列。异常检测模型的主要步骤如图4 所示。
图4 异常检测模型主要步骤
实验中所用到的时间序列数据为北京地区每小时PM数据,数据集来自 UCI Machine Learning Repository,范围为2010⁃01⁃01—2014⁃12⁃31。数据集共43 824 个样本,对于缺失值使用同一天数据的平均值替换,经过处理后的时间序列数据如图5 所示。
图5 PM2.5时间序列数据
对数据进行2 天重采样,即用时间窗口大小为48 h的时序数据作为输入序列,重采样后的数据集共913 个样本。其中使用70%作为训练集,20%作为验证集,10%作为测试集。
本文使用基于Python 的Tensorflow 2 深度学习库构建Bi⁃LSTM深度自编码器模型。实验环境为Windows 10 64 位,CPU 为I7⁃8750h,显卡为GTX 1060 6 GB,内存为8 GB。
首先使用MinMaxScaler 方法将数据归一化,采用顺序方式(Sequential)构建网络模型。编码器和解码器均定义为Bi⁃LSTM 层,共7 层,其单元数量分别为64,48,32,12,32,48,64,前6 层均返回序列。接下来定义Dropout 层,Dropout 比率为0.2。最后一层定义Dense全连接层,共有48 个单元,激活函数为线性整流函数(ReLU)。模型编译时,使用均方误差(Mean Square Error,MSE)作为损失函数(Loss),使用Adam 作为和优化算法(Optimizer),学习率(LR)设为0.000 1。模型训练时,设置批次训练样本数(Batch_size)为32,训练轮次(Epoch)为50。
在实验中,使用重建序列和原始序列对应元素差值的二范数(2⁃Norm)作为重建误差指标。设序列重建前后对应的元素差为向量=(,,…,x),该数值越大说明重建误差越大。重建误差指标如下:
经过50 轮训练后,模型在训练集和验证集上的损失见图6。从图6 可以看出,模型在训练集上的最终损失约为0.000 51,在测试集上的最终损失约为0.000 39。
图6 模型训练损失图
模型训练完成后,将重建异常比率设为0.99,得到重建误差阈值约为0.400 5。模型在训练集和验证集上的异常检测结果如图7 所示。
图7 训练集验证集异常检测结果
从图7 可以知道,模型在训练集和验证集上共检测到10 个异常序列,其编号分别为22,39,40,227,334,376,555,562,711,779。对异常序列711 重建前后进行可视化如图8 所示。
图8 异常序列711 重建结果对比
从图8 可以看出,异常序列711 在前42 h 一直处于较平缓状态,PM值最大在200 μg/m左右。因此模型可以较好地重建这一部分序列,重建误差较小。在43~47 h 之间,PM值先剧增后迅速减少,序列出现剧烈变化。模型无法重建预测这一部分序列,重建误差过大,因此将此序列视为异常。接下来使用模型在测试集上进行检测,结果如图9 所示。从图9 可以看出,模型在测试集上共检测到12 个异常序列,对异常序列901 重建前后进行可视化,如图10 所示。
图9 测试集异常检测结果
图10 异常序列901 重建结果对比
从图10 可以看出,异常序列901 在20 h 左右和25~35 h 的PM值均为0 μg/m,且在35 h 后序列急速上升。模型较好地重建了35 h 后的上升序列,但无法有效重建两段为0 的时间序列,重建误差大于阈值,因此将此序列视为异常。
在时间序列异常检测任务中,除了监督算法外,基于无监督的异常检测方法也值得考虑。本文提出一种新的无监督时间序列异常检测方法,此方法基于Seq2Seq 模型,利用Bi⁃LSTM 深度自编码器对序列的重建效果来发现异常序列。异常序列的发现取决于模型对原始序列的重建效果,该方法能更好地挖掘时间序列中的异常序列模式。通过在空气质量数据上的实验,证明了该方法的可行性,模型初步达到了不错的检测效果,为时间序列异常检测提供了新的方法。