2013-03-13 13 views
7

Mam długie obliczenia, które powtarzam wiele razy. W związku z tym chciałbym użyć zapamiętywania (pakiety takie jak jug i joblib), w porozumieniu z Pandas. Problem polega na tym, czy pakiet dobrze zapamiętałby Pandas DataFrames jako argumenty metody.Panda memoization

Czy ktoś próbował? Czy jest jakiś inny zalecany pakiet/sposób, aby to zrobić?

Odpowiedz

6

Autor dzbanka tutaj: dzbanek działa dobrze. Właśnie próbowałem następujące i działa:

from jug import TaskGenerator 
import pandas as pd 
import numpy as np 


@TaskGenerator 
def gendata(): 
    return pd.DataFrame(np.arange(343440).reshape((10,-1))) 

@TaskGenerator 
def compute(x): 
    return x.mean() 

y = compute(gendata()) 

To nie jest tak efektywny, jak to może być tak, że używa tylko pickle wewnętrznie dla DataFrame (choć spręża je na bieżąco, więc nie jest straszny pod względem wykorzystania pamięci, po prostu wolniej niż mogłoby to być).

będę otwarty na zmiany, które zapisuje je jako szczególny przypadek jak dzbanek aktualnie robi dla tablic numpy: https://github.com/luispedro/jug/blob/master/jug/backends/file_store.py#L102

+0

A co się dzieje, gdy wywołasz' compute (gendata()) '? Czy faktycznie ładuje DataFrame z pamięci podręcznej? – Yariv

+0

Jeśli' ' gendata() '' została obliczona w innym procesie, a następnie tak. – luispedro

+0

Czy istnieje sposób na uruchomienie dzbanka za pomocą komendy 'python' zamiast' jug'? – Light

4

Używam tego podstawowego dekoratora do zapamiętywania, memoized. http://wiki.python.org/moin/PythonDecoratorLibrary#Memoize

DataFrames są nieosiągalne, więc powinno działać poprawnie. Oto przykład.

In [2]: func = lambda df: df.apply(np.fft.fft) 

In [3]: memoized_func = memoized(func) 

In [4]: df = DataFrame(np.random.randn(1000, 1000)) 

In [5]: %timeit func(df) 
10 loops, best of 3: 124 ms per loop 

In [9]: %timeit memoized_func(df) 
1000000 loops, best of 3: 1.46 us per loop 

Wygląda dobrze dla mnie.

+0

Dzięki. Co masz na myśli przez "DataFrames są nieosiągalne"? 'hash (pd.DataFrame ([1,2,3]))' zwraca inną wartość, jeśli wywołasz ją dwukrotnie. – Yariv

+0

Kod dla przypomnienia sprawdza metodę collections.Hashable() przed próbą buforowania danych. Ale twój komentarz sprawia, że ​​zastanawiam się, czy to działa zgodnie z przeznaczeniem. –

+0

DataFrame prawdopodobnie powinien podnieść w tym przypadku, podniosę pr na github –