[TIP / Pandas] Pandas를 보다 올바르게 사용하는 방법

2019. 5. 23. 00:42분석 Python/Pandas Tip

728x90

https://towardsdatascience.com/how-to-use-pandas-the-right-way-to-speed-up-your-code-4a19bd89926d

 

How to use Pandas the RIGHT way to speed up your code

The Pandas library has been a heavenly gift to the Data Science community. Ask any Data Scientist how they like to handle their datasets…

towardsdatascience.com

원글을 참고하면 더욱 좋습니다.

 

Pandas하면 파이썬에서 자주 사용하는 패키지인데요. 

이것이 작은 데이터에서는 할만한데, 큰 데이터를 가끔 다룰 때는 R에서 data.table보다 뭔가 효율도 안나오더라구요. 

판다스는 전체 열이나 컬럼들을 한번에 계산하는 vectorized operation으로 만들어졌다.

그래서 각각의 셀을 Loop도는 것은 만들어진 방식과는 다른 방식이라고 하네요. 

그래서 항상 먼가 Loop 할게 있다면 matrix operation을 하면 좋다고 합니다!!

 

1. 기본 Loop Range 사용하기

import seaborn as sns
import time

data = sns.load_dataset('iris')

def compute_class(petal_length):
    if petal_length <= 2:
        return 1
    elif 2 < petal_length < 5:
        return 2
    else:
        return 3

start = time.time()

class_list = list()
for i in range(len(data)):
    petal_length = data.iloc[i]['petal_length']
    class_num = compute_class(petal_length)
    class_list.append(class_num)

end = time.time()
print("For-loop run time = {}".format(end - start))
## For-loop run time = 0.06366300582885742

 

2. Looping with .iterrows()

저도 보통은 range를 썻는데, iterrows를 쓰면 더 빠르다고 하네요!

enumerate 같은 개념으로 index랑 각각의 열을 뽑아준다고 합니다.

start = time.time()

class_list = list()
for index, data_row in data.iterrows():
    petal_length = data_row['petal_length']
    class_num = compute_class(petal_length)
    class_list.append(class_num)

end = time.time()
print("Iterrows run time = {}".format(end - start))
## Iterrows run time = 0.03499460220336914

3. Dropping loops completely with .apply()

아까 위에 썻듯이 Pandas는 전체 계산을 한꺼번에 하도록 고안을 했으니, Loop는 이제 버리는 것도 항상 생각해봅시다!

apply를 통해 row, col 기준으로 해줄 수가 있습니다!

start = time.time()

class_list = data.apply(lambda row: compute_class(row['petal_length']), axis=1)

end = time.time()
print(".apply() run time = {}".format(end - start))
## .apply() run time = 0.009738683700561523!!

훠월씬 빠르네요! 빠른 이유는 Cython 으로 해서 그렇다네요 그래서 이것을 더 최적화를 잘하면 더 빨라진다고 합니다.

그리고 코드도 굉장히 깔끔하게 한줄로 딱! 

 

4. The final cut

Loop를 고민하지 말고 항상 vectorized operation으로 고안된 것을 생각하라고 합니다!

Loop없이 할 수 있게요!! ..어렵어렵

cut 함수라는게 있다고 합니다 각각의 범위에 대해서 IF-ELSE로 해서 정의해준다고 하고 제일 빠르게 나옵니다.

먼가 잘라서 어딘가 넣을 때는 Cut이 유용하겠네요!

R에서 Cut 함수가 떠오르네요!

start = time.time()

class_list = pd.cut(x=data.petal_length,
                   bins=[0, 2, 5, 100],
                   include_lowest=True,
                   labels=[1, 2, 3]).astype(int)

end = time.time()
print(".cut() run time = {}".format(end - start))
## .cut() run time = 0.00635838508605957!!!!!!!!!!

https://www.youtube.com/watch?v=jdxujfAz1zA

아주 작은 일이라도 조금씩!! 결국 스노우볼이다!

 

728x90