2016-10-21 2 views
1

Я выполняю процедуру, когда на каждой итерации создаются некоторые значения (не так много значений: всего ~ 50 значений на итерацию, из которых некоторые являются короткими 4-5 символьные строки, но большинство из них состоят из 2-3 цифр). Примерно 3 тысячи итераций.Python Pandas, создающий длинный список dataframes, чтобы получить сцепление

В настоящее время я использую фрейм данных pandas для хранения этих значений ~ 50 для заданной итерации, а затем добавьте df в список фреймов данных (dflist), и как только все итерации 3K будут выполнены, я объединяю 3K фреймы данных (так как все они имеют одинаковые имена столбцов), используя что-то вроде:

df_final = pd.concat (dflist, оси = 0)

есть ли лучший способ сделать эту процедуру, например. просто используйте массив numpy и добавьте значения вдоль оси 0, а в конце включите полный массив numpy в кадр данных Pandas с данным набором имен столбцов?

Я спрашиваю, потому что после многих итераций (~ 200 из 3 тысяч), код существенно замедляется, а использование системной памяти медленно ползет вверх, а между итерациями, насколько я могу судить, все мои значения перезаписывается на каждой итерации, за исключением этого списка блоков данных pandas, который, кажется, является единственной вещью, которая растет после каждой итерации. Я использую Python 2.7. Такое поведение возникает, когда я запускаю свой скрипт в графическом интерфейсе Spyder или просто из командной строки.

Еще одна вещь: даже несмотря на то, что значения, которые я фактически сохраняю, относительно малы (значения ~ 50 для каждой итерации), данные, которые я просматриваю для извлечения этих сводных значений, очень велики. Таким образом, исходный csv составляет ~ 10 ГБ с ~ 200 миллионами строк, и я chunk его с помощью pd.read_csv с заданным chunksize, который составляет примерно 50K строк. Затем для этих 50K строк я получаю около 50 значений. Но я бы подумал, что каждый кусок будет независимым, и поскольку значения становятся перезаписанными, использование памяти не должно расти, как это происходит.

Пример ДФ:

CHFAC Bygoper Change MinB NumB NumCombos Total 
0 abc3 574936022 + 1  1 1 11 
1 abc3 574936022 - 1  0 0 0 
2 abc3 574936022 + 2  1 1 11 
3 abc3 574936022 - 2  0 0 0 
4 abc3 574936022 + 5  1 1 11 
5 abc3 574936022 - 5  0 0 0 
6 abc3 574936022 + 10 1 1 11 
7 abc3 574936022 - 10 0 0 0 
+0

показывают нам одну или 2 образца ДФ вы CONCAT, это трудно сказать, сколько столбцов у вас есть, индекс и такие на основе вашего поста. –

ответ

0

Вы можете быть творческими и использовать список для хранения данных, а затем создать свой окончательный dataframe в конце цикла. Трудно использовать ваш пример, поскольку мы не имеем представления о вашем процессе создания. Я дам общий ответ, показывающий создание dataframe в 2 колонки на основе цикла 10 итераций, где каждая итерация имеет различную длину выхода

import pandas as pd 
from random import randint 
col1_val, col2_val = [], [] 
for i in range(10): 
    random_len = range(randint(0, 9)) 
    col1 = random_len 
    col2 = random_len 
    col1_val.extend(col1) 
    col2_val.extend(col2) 
pd.DataFrame({'col1':col1_val, 'col2':col2_val}) 

Out [110]:

col1 col2 
0  0  0 
1  1  1 
2  2  2 
3  3  3 
4  4  4 
5  0  0 
6  1  1 
7  2  2 
8  3  3 

теперь давайте посмотрите на скорость, используя метод списка:

import time 
st = time.time() 
col1_val, col2_val = [], [] 
for i in range(10000): 
    random_len = range(randint(0, 9)) 
    col1 = random_len 
    col2 = random_len 
    col1_val.extend(col1) 
    col2_val.extend(col2) 
pd.DataFrame({'col1':col1_val, 'col2':col2_val}) 
print time.time()-st 
0.0499999523163 

с помощью метода:

st = time.time() 
dflist = [] 
for i in range(10000): 
    random_len = range(randint(0, 9)) 
    col1 = random_len 
    col2 = random_len 
    dflist.append(pd.DataFrame({'col1':col1, 'col2':col2})) 
pd.concat(dflist) 
print time.time()-st 
7.21199989319 

так для 10000 итераций, было бы о 180x быстрее

+0

Итак, это должно быть улучшением по сравнению с текущим методом добавления к списку данных. Итак, каковы различия в производительности предложенного вами метода расширения столбца: col1_val.extend (col1) и добавление сразу всех этих значений в массив numpy? Например. vals = np.vstack ((vals, [1,2])) для примера с двумя столбцами? – sambajetson

+0

@sambajetson, расширяющий или добавляющий массив numpy, не очень эффективен по памяти, и я бы не рекомендовал этого.вы можете [прочитать этот ответ] (http://stackoverflow.com/questions/13215525/how-to-extend-an-array-in-place-in-numpy) в качестве примера того, почему вы не должны так поступать –

 Смежные вопросы

  • Нет связанных вопросов^_^