Python 为分组数据的RNN生成具有特定长度的序列/批

Python 为分组数据的RNN生成具有特定长度的序列/批,python,pandas,numpy,tensorflow,keras,Python,Pandas,Numpy,Tensorflow,Keras,当我希望将不同组的数据传递到RNN中时,问题就出现了——大多数示例都假设了优雅的时间序列,但在添加组时,我们不能简单地在数据帧上加窗口,我们需要在组更改时跳转,以便数据来自组内 这些群体只是不同的人,所以我想保留他们的序列。例如,用户浏览网站并收集页面浏览数据。也可能是不同的股票及其相关的价格变动 import pandas as pd data = { 'group_id': [1,1,1,1,2,2], 'timestep': [1,2,3,4,1,2], 'x':

当我希望将不同组的数据传递到RNN中时,问题就出现了——大多数示例都假设了优雅的时间序列,但在添加组时,我们不能简单地在数据帧上加窗口,我们需要在组更改时跳转,以便数据来自组内

这些群体只是不同的人,所以我想保留他们的序列。例如,用户浏览网站并收集页面浏览数据。也可能是不同的股票及其相关的价格变动

import pandas as pd
data = {
    'group_id': [1,1,1,1,2,2],
    'timestep': [1,2,3,4,1,2],
    'x': [6,5,4,3,2,1],
    'y': [0,1,1,1,0,1]
}
df = pd.DataFrame(data=data)


   group_id  timestep  x  y
0         1         1  6  0
1         1         2  5  1
2         1         3  4  1
3         1         4  3  1
4         2         1  2  0
5         2         2  1  1
假设我们希望使用2个样本的批量大小,每个样本将有3个时间步<代码>RNN序列。_len__=3(以下)批,但这是不可能的,因为我们最多可以从第一组(即1批)中获得2个样本。第二组只有2个时间步,因此不可能进行迭代

from keras.utils import Sequence

class RNNSequence(Sequence):

    def __init__(self, x_set, y_set, batch_size, seq_length):
        self.x, self.y = x_set, y_set
        self.batch_size = batch_size
        self.seq_length = seq_length

    def __len__(self):
        return int(np.ceil(len(self.x) / float(self.batch_size)))

    def __getitem__(self, idx):
        # get_batch to be coded
        return get_batch(idx, self.x, self.y, self.batch_size, self.seq_length)
使用序列获取这些批次的最有效方法是什么

我的解决方案是实际上不使用序列,而是使用一个定制的生成器,在不知道会有多少批次的情况下输出数据。并使用
fit\u生成器(自定义生成器,最大队列大小=批量大小)
。这是最有效的方法吗?这里的问题是没有洗牌,这可能是个问题

batchsize=2,seq_length=3的期望输出为:

X = [ 
        [ [6], [5], [4] ], 
        [ [5], [4], [3] ] 
    ]

Y = [ 1, 1 ]

似乎您不仅需要知道批次的数量,还需要能够在给定批次号的情况下输出任何批次。您可以在
RNNSequence.\uuuu init\uuuu
或更早版本中创建所有样本的索引,然后从中组装批次。在
\uuuu getitem\uuuu
中,您可以相应地输出批次

这个快速而肮脏的伪代码应该说明示例索引的概念。如果需要,您可以决定使用pandas或numpy中的函数等

# Pseuducode for generating indexes for where samples start.
seq_len = 3
sample_start_ids = []
for group_id, group in enumerate(groups):
    for timestep_id, timestep in enumerate(group_timesteps):
        # Only add as sample if it is the first
        # timestep in the group or if a full sample fits.
        if timestep == 1 or timestep <= len(group_timesteps) - seq_len+1:
            sample_start_ids.append((group_id, timestep_id))

num_samples = len(sample_start_ids)

# Group the samples into batches of appropriate size.
pass

num_batches = len(your_batches)
用于为样本的起始位置生成索引的Pseuducode。 序号=3 示例\u开始\u ID=[] 对于组id,枚举中的组(组): 对于timestep\u id,枚举中的timestep(组\u timesteps): #如果是第一个,则仅添加为示例 #组中的时间步长,或者如果完整样本适合。
如果timestep==1或timestep,谢谢。我来试试这个。你认为用可变长度的序列来代替会更有效吗?但是缩小规模后,序列的批大小将为1?我建议的伪代码假设(可能是错误的,我现在怀疑)每个原始序列至少需要一个样本。批次中不同长度的样本可能需要一些变通方法。最简单的方法是输入长度恒定的序列,或者使用1的批量大小。我没有一个关于什么对你的问题最有效的具体建议。不,你假设正确,我想测试两种不同的方法。一个是可变长度的,一个是固定序列长度的:)如果社区中没有其他成员的输入,我会将其标记为正确!