1000x faster data manipulation: np.where() & np.select()

jj·2021년 3월 26일
0

나도 몰랐던 pandas

목록 보기
3/3

글을 작성하기 위해 참고한 영상 출처: https://www.youtube.com/watch?v=nxWginnBklU
이미지 출처: https://www.goodgag.net/162984

오늘 아침에 유튜브가 추천해준 영상의 제목이 흥미로워서, 침대에 누운채로 한번 봐봤다.
유용한 영상이었다.
까먹기 전에 정리를 하고 가본다.

INTRO


왼쪽 함수에서 오른쪽 함수로 갈 때, 어떤 점이 바뀌었을까?
함수에 전달해주는 인자가 바뀌었다.
두 함수 모두 pd.apply()에 적용 가능하지만, 왼쪽은 row를 그대로 전달했기 때문에, 함수 안에서 row['cs']와 row['st']를 찾는 시간이 더 걸릴것이다. 그래서 오른쪽처럼 처음부터 인자를 두개로 정해서 전달해주면 어떻게 될까?
ValueError: The truth value of a series is ambiguous
이 말은 "내가 지금 col1 == 'None'을 비교해야되는데, 이 비교할 col1이 전체 series를 의미하는 것인지, col1 안의 하나의 row 값에 대해서 비교하는 것인지 불명확하다"는 뜻의 꾸지람이다.

그래서 이 발표의 화자 Nathan씨는 화가 났다.
logical statement를 vectorize할 수는 없는 것인가??

여기서 vectorize는 간단하게 말해서, scalar 값(하나의 원소)들을 모두 하나의 vector(list나 numpy array같은 늬낌)에 넣어서, 더 큰 범주에서 한번에 연산을 처리할 수 있고, loop을 돌지 않아도 된다는 것이다.
예를 들어 당근10개를 모두 갈아야 되는데, 당근을 한 개씩 x10번 가는 것보다 당근 10개 x1번 가는 것이 더 편하니까.. 어디까지나 간단한 설명이다)

그래서 해결법은 다음과 같다

np.where을 쓰자


저기 하이라이트 친 .values는 안써도 되는데, 쓰면 좀더 speed up 시킬 수 있다고 한다. series.values를 하게 되면, 우리의 series(index와 column이 덕지덕지 붙은 친구)에서 numpy의 array의 원소들(순수한 데이터 값 그자체)로 허물을 벗게 된다. 그래서 computation이 handle할 대상이 훨씬 줄어들게 되고, 속도도 향상되게 된다.

백문이불여일견, 결과를 한번 두 눈 뜨고 비교해보면?
제목에 쓴 그대로, 약 1000배 빨라진다!!

multiple condition의 경우에는? numpy.select()를 쓰자!

앞에서 쓴 np.where을 여러번 적용할 수 도 있지만, 더 나은 방법이 있다!

conditions와 choices를 따로 묶어주니 더 깔끔하고 이뻐졌다!(dafault 인자는 else일 경우에 return 할 값을 넣어주면 된다)
nested if else statement의 경우에는 다음과 같이 & 처리해주면 된다.
결과

더 복잡한 condition의 경우에는?

  • strings
  • dictionaries
  • dates
  • other rows

strings

가장 쉬운 vectorize방법은 pandas의 str method를 쓰는 것이다 결론을 보면 이번에는 큰 속도 향상이 보이지 않는다?
Nathan씨가 말하길 vectorizing이 항상 빨라지는 것은 아니라고 한다. .apply(looping method)가 더 빠를 때도 있단다..!

dictionaries -> .map method

python dictionary를 look up해야하는 경우가 있을 때, .map method를 쓸 수 있다!

dates


첫번째 방법은 dt accessor를 쓰는 것이다. 간단하게 .days앞에 .dt accessor를 붙여주면 끝이다
두번째 방법은 timedelta로 형변환을 하는 것이다.진짜 1000배가 빨라졌다..!!

values from other rows

이거는 .shift() 방법을 썼는데, 사실 이거는 어떤 쿼리를 날릴것인가에 따라 .shift()를 쓸 수도 있고 못 쓸 수도 있기에...

더..더..! 복잡한 경우에는?

정리!

profile
재밌는게 재밌는거다

0개의 댓글