Закрепление генерации последовательности данных в массив с использованием Python - PullRequest
0 голосов
/ 24 июня 2019

У меня есть следующий код для создания последовательностей кадра данных, который загрузил данные CSV о коэффициентах дождей.

import pandas as pd
import numpy as np
import sklearn
import sklearn.preprocessing
seq_len  = 1100

def load_data(df_, seq_len):
    data_raw = df_.values # convert to numpy array
    data = []
    data = np.array([data_raw[index: index + seq_len] for index in range(len(data_raw) - (seq_len+1))])
    print(data.shape)

df = pd.read_csv("data.csv",index_col = 0)
temp = df.copy()
temp = normalize_data(temp)
load_data(df_, seq_len)temp

Когда я запустил функцию load_data(df_, seq_len)temp, мне пришлось ждать много времени. Я не понимаю, является ли это проблемой seq_len.

Вот прикрепленный набор данных: data.csv

Пожалуйста, помогите мне сделать это быстрее. Может случиться так, что в будущем у меня будет больше данных. Но если это станет быстрее, мне не нужно беспокоиться о будущих данных. ** РЕДАКТИРОВАНИЕ: ** Согласно @ParitoshSingh Comment .. Вот часть набора данных. Но не считайте, что это данные. Это просто часть больших данных:

,rains_ratio_2013,rains_ratio_2014
0,1.12148,1.1216
1,1.12141,1.12162
2,1.12142,1.12163
3,1.12148,1.1216
4,1.12143,1.12165
5,1.12141,1.12161
6,1.1213799999999998,1.12161
7,1.1214,1.12158
8,1.1214,1.12158
9,1.12141,1.12158
10,1.12141,1.12161
11,1.12144,1.1215899999999999
12,1.12141,1.12162
13,1.12141,1.12161
14,1.12143,1.12161
15,1.12143,1.1216899999999999
16,1.12143,1.12173
17,1.12143,1.12178
18,1.1214600000000001,1.12179
19,1.12148,1.12174
20,1.12148,1.1217
21,1.12148,1.12174
22,1.12148,1.1217
23,1.12145,1.1217
24,1.12145,1.1217
25,1.12148,1.1217
26,1.1214899999999999,1.1217
27,1.1214899999999999,1.1216899999999999
28,1.12143,1.1216899999999999
29,1.12143,1.1216899999999999
30,1.12144,1.1216899999999999

1 Ответ

0 голосов
/ 24 июня 2019

По сути, это проблема со скользящим окном.

Один из подходов заключается в использовании векторизации для более быстрого перемещения скользящих окон по данным. Обратите внимание: если у вас недостаточно памяти для загрузки окончательных выходных данных, это также может вызвать проблемы.

import numpy as np
import pandas as pd

Создание фиктивного фрейма данных для простоты использования. Вы должны проверить на своем исходном фрейме данных.

seq_len = 5
df = pd.DataFrame(np.arange(300).reshape(-1, 3))
print(df.head())
#Output:
    0   1   2
0   0   1   2
1   3   4   5
2   6   7   8
3   9  10  11
4  12  13  14

Теперь мы можем создать массив для всех индексов, которые нам нужно использовать, и использовать индексирование для доступа ко всем нашим значениям в нужном формате.

def load_data(df_, seq_len):
    data_raw = df_.values # convert to numpy array
    #find total number of rows
    nrows = len(data_raw) - seq_len + 1 #Your code had -(seq_len + 1) for some reason. i am assuming that was just a mistake. If not, correct this accordingly.
    #Now, create an index matrix from the total number of rows.
    data = data_raw[np.arange(nrows)[:,None] + np.arange(seq_len)] 
    print("shape is", data.shape)
    return data

out = load_data(df, seq_len)
#Output: shape is (98, 3, 3)

РЕДАКТИРОВАТЬ: Если вы столкнулись с ошибками памяти, вы всегда можете изменить функцию, чтобы использовать генератор вместо. Таким образом, вы занимаетесь промежуточным положением между двумя сценариями итерации один за другим или слишком большим объемом памяти.

def load_data_gen(df_, seq_len, chunksize=10):
    data_raw = df_.values # convert to numpy array
    nrows = len(data_raw) - seq_len + 1
    for i in range(0, nrows, chunksize):
        data = data_raw[np.arange(i, min(i+chunksize, nrows))[:,None] + np.arange(seq_len)]
        print("shape is", data.shape)
        yield data

out = load_data_gen(df, seq_len, 15)
test = list(out)
#Output:
shape is (15, 5, 3)
shape is (15, 5, 3)
shape is (15, 5, 3)
shape is (15, 5, 3)
shape is (15, 5, 3)
shape is (15, 5, 3)
shape is (6, 5, 3)
...