해당 내용은 Datacamp의 Data engineering track을 정리했습니다.
Writing Efficient Python Code의 chapter 2에 대한 내용입니다.
기본적인 내용보다는 강의를 들으면서 처음 알게 된 내용을 위주로 작성했습니다.
해당 포스팅에는 아래의 내용을 포함하고 있습니다.
- runtime 측정하기(%timeit)
- 병목구간 찾기(line_profiler)
- 메모리 문제 구간 찾기(memory_profiler)
1. Examining runtime
이전 강의를 통해 좋은 코드는 빠르게 실행할 수 있어야 하며, 적은 메모리를 사용하는 것이 중요한 것을 알 수 있었습니다. 이번 강의에서는 해당 지표들을 어떻게 측정할 수 있는지를 알아봅니다.
가장 먼저 알아볼 것은 IPython magic command인 %timeit을 통해서 runtime을 계산할 수 있습니다. 여기서, magic command는 Prefix로 %를 사용할 수 있습니다. 다양한 command가 존재하는데, 알고 싶다면 %lsmagic으로 확인하실 수 있습니다.
import numpy as np
%timeit rand_nums = np.random.rand(1000)
위의 코드블럭처럼 원하는 코드 앞에 %timeit을 붙여주면 되고, 결과는 아래와 같습니다.
%timeit은 맨 앞에 평균 실행시간과 표준편차를 뒤에 run과 loop값은 총 run에 해당하는 만큼 구해서 평균낸 값들을 loop만큼 합쳐서 평균을 구합니다. 만약, n과 r값을 수정하고 싶다면, %timeit -r2 -n10으로 수정할 수 있습니다. 여기서 r은 run에 해당하며, n은 loop 횟수에 해당합니다. %timeit을 활용해서 dict()와 {}의 속도를 비교해보면 후자가 더 빠른 것을 알 수 있습니다. 만약에 여러 줄에 해당하는 코드를 확인하기 위해서는 %%timeit으로 확인할 수 있습니다.
2. Code profiling for runtime
이번에는 코드가 여러 줄 존재할 때, 어떤 구간에서 오래걸리는지 확인할 수 있는 라이브러리를 소개합니다. line_profiler라는 라이브러리를 활용하는데, pip install line_profiler로 간단하게 실행할 수 있습니다. line_profiler는 %load_ext line_profiler를 통해서 세션에 로드한 뒤 %lprun -f 함수명 함수명(인수)로 확인할 수 있습니다.
%load_ext line_profiler
%lprun -f convert_units convert_units(heroes, hts, wts)
위와 같은 결과를 얻을 수 있으며, 각 라인별로 어느정도의 시간이 사용되고 있는지를 확인할 수 있습니다.
3. Code profiling for memory usage
메모리 할당량을 확인하는 방법에는 sys.getsizeof로 확인할 수도 있지만 위에서 line_profiler와 비슷하게 memory_profiler를 활용할 수 있습니다. 단, 사용할 때 import된 function만 사용이 가능합니다.
from hero_funcs import convert_units
%load_ext memory_profiler
%mprun -f convert_units convert_units(heroes, hts, wts)
위의 결과를 얻을 수 있고, 각 라인마다 얼마나의 용량을 사용하고 있는지 확인할 수 있습니다. Increment는 이전 라인보다 얼마나 더 사용했는지 확인할 수 있습니다.