2015-05-28 5 views
7

Я путаюсь с использованием памяти python для функции. Я запускаю функцию, в которой возвращается dataframe pandas (1161 X 240), и аргументы (bamfile, pandas.Dataframe (1161 X 50)).Выделение памяти для цикла в python

Теперь я предоставлю использование памяти профилировщика:

Line # Mem usage Increment Line Contents 
================================================ 
    120 983.363 MiB 0.000 MiB @profile 
    121        def overlapping_peaks_distribution(bam_peak1, overlap_df): 
    122         ''' 
    123         Returns dataframe for tag count distribution for overlapping peaks within 500bp (+,-) from summit. 
    124         This function also considers the gene transcrition direction. 
    125         :param bam_peak1: 
    126         :param overlap_df: 
    127         :return: 
    128         ''' 
    129 983.363 MiB 0.000 MiB  import pandas as pd 
    130 983.363 MiB 0.000 MiB  import sys 
    131 983.363 MiB 0.000 MiB  peak_distribution_sample = pd.DataFrame() 
    132 983.363 MiB 0.000 MiB  print 'Process: Feature extraction from BAM started' 
    133 1783.645 MiB 800.281 MiB  for ind, row in overlap_df.iterrows(): 
    134 1782.582 MiB -1.062 MiB   sys.stdout.write("\rFeature extraction for peak:%d" % ind) 
    135 1782.582 MiB 0.000 MiB   sys.stdout.flush() 
    136 1782.582 MiB 0.000 MiB   chr = str(row['chr']) 
    137 1782.582 MiB 0.000 MiB   orientation = row['Next transcript strand'] 
    138 1782.582 MiB 0.000 MiB   middle = row['start'] + row['summit'] 
    139 1782.582 MiB 0.000 MiB   start = middle - 3000 
    140 1782.582 MiB 0.000 MiB   stop = start + 50 
    141 1782.582 MiB 0.000 MiB   list_sample1 = [] 
    142          #total_tags = int(bam_peak1.mapped) will get total no of mapped reads 
    143        
    144 1782.586 MiB 0.004 MiB   for i in range(0, 120): 
    145 1782.586 MiB 0.000 MiB    tags1 = bam_peak1.count(chr, start, stop) 
    146 1782.586 MiB 0.000 MiB    start = stop 
    147 1782.586 MiB 0.000 MiB    stop = start + 50 # divide peaks into length of 25 bp 
    148 1782.586 MiB 0.000 MiB    list_sample1.append(tags1) 
    149 1782.586 MiB 0.000 MiB   if orientation > 0: # Direction gene transcription 
    150           #print 'Towards 5 prime' 
    151 1780.883 MiB -1.703 MiB    peak_distribution_sample = peak_distribution_sample.append(pd.Series(list_sample1), ignore_index=True) 
    152          else: 
    153           #print 'Towards 3 prime' 
    154 1783.645 MiB 2.762 MiB    peak_distribution_sample = peak_distribution_sample.append(pd.Series(list_sample1[::-1]), ignore_index=True) 
    155         #print peak_distribution_sample 
    156 1783.645 MiB 0.000 MiB  return peak_distribution_sample 

Я не понимаю, почему в линии 133 он увеличивает (безумную диски емкостью 800 Мбайт). Это поглощает все пространство в моей памяти. Я не знаю, это какая-то ошибка от меня?

Я использовал объектный граф для поиска утечек памяти. Номер объекта до функции начала:

(Pdb) objgraph.show_most_common_types() 
function     15293 
tuple      4115 
dict      3086 
cell      2670 
list      2107 
weakref     1834 
wrapper_descriptor   1760 
builtin_function_or_method 1655 
getset_descriptor   1235 
type      1232 

Количество объектов после функции завершения.

(Pdb) import objgraph 
(Pdb) objgraph.show_growth() 
function      16360  +1067 
dict       3546  +460 
list       2459  +354 
tuple       4414  +306 
getset_descriptor    1508  +273 
builtin_function_or_method  1895  +240 
weakref      2049  +215 
module       593  +123 
wrapper_descriptor    1877  +117 
type       1341  +109 

Мы можем видеть значительное увеличение объектов. Я также произвел некоторый график. enter image description here

Я считаю, что коробка красный шрифт предполагают, чтобы быть освобождены, но они не являются.

+2

Вполне возможно, что 'overlap_df.iterrows()' загружает это полностью в память перед началом первой итерации. – SuperBiasedMan

+0

https://github.com/pydata/pandas/issues/7683 –

+0

Это может быть проблемой, но как освободить эту память. –

ответ

0

Уверены ли вы, что он не показывает общий размер overlap_df?

Существует аналогичная вещь здесь:

144 1782,586 MiB 0,004 MiB для г в интервале (0, 120):

Profiler показывает общий размер списка 120 Интс как 400 КБ ,

+0

Это означает, что overlap_df имеет размер 800 МБ. Это невозможно, потому что в физической памяти это занимает 8 МБ. Я читал, что с каждой итерацией он выделяет память, но не освобождает ее. В конце функция заканчивается печатью out_of_memory(). Я также пробовал ** gc.collect() **, но это не влияет. вложенные петли делают это хуже. –

0

Я нашел утечку памяти. Это произошло из-за стороннего модуля (pysam), который имел утечку памяти.

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

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