Keras卷积1D通道独立,[样本,时间步长,特征],风力涡轮机数据集

时间:2018-05-25 12:06:31

标签: tensorflow keras deep-learning conv-neural-network convolution

我正在开发一种风力涡轮机数据集,它具有常规矩阵格式:[row:datetime,column:features]

但我想用卷积捕获这些功能的进展,就像在LSTM中完成的那样。所以,我已经生成了一个具有以下维度的新数据集:

[datetime,15 timesteps,128 features]:每个原始日期时间行现在有15个寄存器连接在一起(t-0,t-1,...,t-14)。

我的计划是在每个特征(通道)的时间步长维度上分别用大小为1x5和步长为5的内核进行卷积。获取每个DateTime(批处理),来自128个特征的3个长度为5的过滤器,输出形状是(无,3,128)。

然后我将max-pooling应用于前一个第二维(3)结果,以获得期望输出大小的“最重要的复杂时间步长”:(无,1,128)

最后我连接了一个密集的二层分类层。

当前的网络架构在keras中实现如下:

model.add( Conv1D(padding = 'valid',filters = nfeatures,strides = 5,kernel_size = 5, 
                  activation = 'relu',input_shape = (timesteps,nfeatures)) )
model.add( MaxPooling1D() )
model.add(Dropout(0.5))
model.add(Dense(1, activation='sigmoid'))

问题是,当我检查第一层(conv1d)的权重时,权重具有以下维度:[5,128,128]和偏差[128]。

预期权重格式为:[5,1,128]为什么是5x128x128? ,我想为每个功能/频道只需要5个权重(内核大小)。

谢谢!

1 个答案:

答案 0 :(得分:3)

标准卷积文件管理器:

为了获得很好的结果,神经网络很少单独考虑一个特征,相反,它们会促进特征之间的相关性以提取更智能的结果。

这就是标准卷积滤波器形状的原因:

(width, input_features, output_features)   

在此卷积中,所有输入要素都被视为创建新的输出要素。

如何完全个性化功能?

  

警告:这对所有功能使用相同的精确过滤器(每个功能可能需要一个单独的过滤器,然后查看下一个答案)

您可以重新排序数据,使功能成为主要组,并使每个组只有一个功能和过滤器。

然后可以与TimeDistributed图层并行处理这些组。

model = Sequential()

#reordering data and adding 1 dummy feature per group    
model.add(Permute((2,1), input_shape = (timesteps,nfeatures))) #(batch, feat, steps)    
model.add(Lambda(lambda x: K.expand_dims(x))) #(batch, feat, steps, 1)

#applying the 1 filter convolution for each group
model.add(TimeDistributed(Conv1D(padding = 'valid',filters = 1,strides = 5,
                                 kernel_size = 5, activation = 'relu')))
model.add( TimeDistributed(MaxPooling1D()) )

#restoring to (batch,features)    
model.add(Reshape((nfeatures,)))
model.add(Dropout(0.5))
model.add(Dense(1, activation='sigmoid'))

老实说,使用标准卷积,您的模型会更强大,但您可能有特殊原因这样做。

每个功能一个单独的过滤器

这需要更多的工作。我们需要一个实现depthwise_conv1d的自定义层(Keras不提供),或者我们创建128个单独的conv1D层和1个过滤器(更简单)。

使用第二种方法(多重转换层),我们需要一个功能API模型来制作并行的brances。

from keras.model import Model

#function to split the input in multiple outputs
def splitter(x):
    return [x[:,:,i:i+1] for i in range(nfeatures)]


#model's input tensor 
inputs = Input((timesteps,nfeatures))

#splitting in 128 parallel tensors - 128 x (batch,15,1)
multipleFeatures = Lambda(splitter)(inputs)

#applying one individual convolution on each parallel branch
multipleFeatures = [
   Conv1D(padding = 'valid',filters = 1,strides = 5, kernel_size = 5)(feat) 
   for feat in multipleFeatures ]

#joining the branches into (batch, 3, 128)
joinedOutputs = Concatenate()(multipleFeatures)
joinedOutputs = Activation('relu')(joinedOutputs)

outputs = MaxPooling1D()(joinedOutputs)
outputs = Lambda(lambda x: K.squeeze(x,axis=1))(outputs)
outputs = Dropout(0.5)(outputs)
outputs = Dense(1, activation='sigmoid')(outputs)

model = Model(inputs,outputs)