W Zendesk używamy Pythona do budowania produktów uczenia maszynowego (ML). Jednym z powszechnych problemów wydajnościowych, które napotkaliśmy w aplikacjach uczenia maszynowego są wycieki pamięci i spikes. Kod Pythona jest zazwyczaj wykonywany w kontenerach za pomocą frameworków przetwarzania rozproszonego, takich jak Hadoop, Spark i AWS Batch. Każdemu kontenerowi przydzielana jest stała ilość pamięci. Gdy wykonanie kodu przekroczy określony limit pamięci, kontener zostanie zamknięty z powodu błędów braku pamięci.
Szybką poprawką jest zwiększenie przydziału pamięci. Jednak może to spowodować marnotrawstwo zasobów i wpłynąć na stabilność produktów z powodu nieprzewidywalnych skoków pamięci. Przyczyny wycieków pamięci mogą obejmować:
- lingowanie dużych obiektów, które nie są zwalniane
- cykle referencyjne w kodzie
- podstawowe biblioteki/rozszerzenia przeciekające pamięć
Przydatnym ćwiczeniem jest profilowanie użycia pamięci przez aplikacje, aby lepiej zrozumieć wydajność przestrzenną kodu i używanych pakietów bazowych. Ten post obejmuje:
- profilowanie użycia pamięci w aplikacji w czasie
- jak sprawdzić użycie pamięci w określonej części programu
- wskazówki dotyczące debugowania problemów z pamięcią
Możesz spojrzeć na użycie pamięci zmieniające się w czasie podczas wykonywania kodu Pythona używając pakietu memory-profile.
# install the required packages
pip install memory_profiler
pip install matplotlib# run the profiler to record the memory usage
# sample 0.1s by defaut
mprof run --include-children python fantastic_model_building_code.py# plot the recorded memory usage
mprof plot --output memory-profile.png
Opcja include-children powoduje uwzględnienie wykorzystania pamięci przez procesy potomne wywołane przez proces macierzysty. Wykres A przedstawia iteracyjny proces trenowania modelu, który powoduje cykliczny przyrost pamięci w miarę przetwarzania kolejnych partii danych treningowych. Obiekty są uwalniane po rozpoczęciu zbierania śmieci.
Jeśli użycie pamięci stale rośnie, istnieje potencjalny problem wycieków pamięci. Oto przykładowy skrypt, który to zobrazuje.