[Pandas] 데이터프레임 조건에 따른 행 선택 및 변경 (Select Row with condition)

반응형

Pandas Image

* 전체 코드

import pandas as pd
from pydataset import data
df = data('Titanic') ### 테스트 데이터셋 불러오기
### 비교 연산
cond_adult = df.Age=='Adult' # == 연산
df[cond_adult] # True인 값들만 출력
cond_freq_under4 = df.Freq<4 # < 연산
df[cond_freq_under4] # True인 값들만 출력
cond_isin_crew_1st = df.Class.isin(['Crew','1st']) ## isin 연산
df[cond_isin_crew_1st] # True인 값들만 출력
df[~df.Class.isin(['Crew','1st'])] # ~(not 연산)
### 여려 조건 합치기
df[(cond_adult) & (cond_freq_under4)] # &(and)
df[cond_adult | cond_freq_under4] # |(or)
df[(cond_adult) & ~(cond_freq_under4)] # ~(not)
#### 컬럼 지정해서 바꾸기
df.loc[(cond_adult) & (cond_freq_under4),"Class"] = "해적"
#### 행 전체 바꾸기
df.loc[(cond_adult) & (cond_freq_under4)] = ["해적왕", "여자", "GodMother", "Yes", 100]

 

1. 배경

판다스의 DataFrame을 사용하다 보면, 조건에 따라 행들을 선택하고 싶은 경우가 굉장히 많습니다. SQL로 따지면, Select From Where 절을 사용하는 느낌입니다. 판다스에선 조건에 따라 행들을 선택해서 바로 데이터 프레임으로 볼 수 있습니다. 또한, 조건에 따라 선택된 행들의 값을 바로 변경할 수 도 있습니다. 이번 시간엔 그 방법들을 예시와 함께 자세히 알아보겠습니다.

 

2. 조건에 따른 행 선택 (Select Row)

1) 테스트 데이터 불러오기

import pandas as pd
from pydataset import data
df = data('Titanic')
df.head(10)

* 코드 설명

pandas라이브러리와 pydataset의 data 모듈을 import 합니다. 'Titanic' 데이터셋을 불러오고 출력합니다.

* 출력

테스트 데이터 확인

* 각 칼럼(열) 별 값의 종류 확인

for c in df:
print(f"{c:<8} 컬럼 값: {sorted(df[c].unique())}"

* 코드 설명

df를 반복하면 각 칼럼(열)의 이름이 c로 반복됩니다. f-string을 이용해 칼럼이름(c)를 8 단어에 걸쳐(왼쪽 정렬)하고, 컬럼 값을 출력합니다. 칼럼 값은 sorted(df[c].unique()) 코드를 사용했는데, 해당 칼럼의 값의 종류(유니크한 값들)를 정렬(sorted)해서 리스트로 출력하겠다는 뜻입니다. (f-string 정렬 관련 포스팅: [Python] f-string 포맷팅2 (2,8,16 진수, 1000단위 쉼표, 정렬, 문자채우기))

* 출력

컬럼별 값의 종류 출력

 

2) 비교 연산

비교 연산 설명
== 값이 같은 경우
!= 값이 다른 경우
<, <= 값이 작은 경우, 작거나 같은 경우
>, >= 값이 큰 경우, 크거나 같은 경우
cond_adult = (df.Age=='Adult')
cond_adult # 조건에 따른 True, False 값
df[cond_adult] # True인 값들만 출력

* 코드 설명

df에서 Age가 'Adult'인 경우를 구해봅니다. cond_adult에는 시리즈 형태로, 각 Row별로 Adult이면 True, Adult가 아니면 False형태로 값들이 들어있습니다. 이것을 df[cond_adult]로 넣어주면 True인 값들에 해당하는 행들만 데이터 프레임으로 출력해줍니다.

* 출력

조건식 출력 및 조건식을 적용한 데이터프레임 출력

 

cond_freq_under4 = df.Freq<4 # Freq이 4 미만인 경우
df[cond_freq_under4]

* 코드 설명

df.Freq<4은 Freq칼럼의 값이 4 미만인 경우에 대한 시리즈 값입니다. 이를 cond_freq_under4에 저장합니다. 여기서 cond란 condition(조건)의 줄임말입니다. 그리고 df[cond_freq_under4]를 통해 Freq이 4 미만인 경우를 데이터 프레임으로 출력합니다.

* 출력

Freq이 4 미만인 경우 데이터프레임 출력

 

3) isin 연산

cond_isin_crew_1st = df.Class.isin(['Crew','1st'])
df[cond_isin_crew_1st]

* 코드 설명

isin연산은 df.컬럼.isin([리스트]) 형태로 사용합니다. 해당 칼럼에 대해, 리스트에 포함된 값들을 True로 반환합니다. df.Class.isin(['Crew', '1st'])Class 칼럼에 'Crew' 나 '1st'가 포함되어 있는 경우 모두를 의미합니다. 

* 출력

isin 연산 결과 데이터프레임 출력

 

4) not 연산

df[~df.Class.isin(['Crew','1st'])]

* 코드 설명

not 연산은 특정 조건(condition) 앞에 물결표('~')를 붙이면 됩니다. 위 예시를 보면, Class가 Crew나 1st인 조건 앞에 "~"를 붙임으로써, Crew나 1st가 아닌 경우로 조건이 바뀌었습니다.

* 출력

not 연산 결과 데이터프레임 출력

 

5) 여러 조건식 합치기

조건간 연산자 설명
& and를 의미.
| or을 의미.
### 여려 조건 합치기
df[(cond_adult) & (cond_freq_under4)] # &(and)
df[cond_adult | cond_freq_under4] # |(or)
df[(cond_adult) & ~(cond_freq_under4)] # ~(not)

* 코드 설명

&는 조건 간 and 연산을 하며, |는 조건 간 or 연산을 합니다. ~(not 연산)과 함께 쓸 수도 있습니다. 위 3가지 예시를 보겠습니다.

  • df[(cond_adult) & (cond_freq_under4)] : 위에서 정의한 Age가 Adult인 경우 그리고, Freq이 4 미만인 경우를 의미합니다. 즉, Age가 Adult 이면서, Freq이 4 미만인 경우가 출력됩니다.
    * 출력 1

&(and) 조건 예제 출력

  • df[cond_adult | cond_freq_under4] : Age가 Adult 이거나, Freq이 4 미만인 경우입니다. 두 경우중 하나라도 참이면 출력됩니다.
    * 출력 2

  • df[(cond_adult) & ~(cond_freq_under4)] : Age가 Adult인 경우와 Freq이 4 미만이 아니고, 4 이상인 경우를 의미합니다. 즉, Age가 Adult이고, Freq이 4 이상을 동시에 만족하는 경우 출력됩니다.
    * 출력 3

&(and)와 ~(not) 같이 사용한 예제 출력

 

3. 선택한 값 바꾸기 (Chage Row)

위에서는 조건을 통해 행을 선택하는 방법을 알아보았습니다. 선택한 행의 값을 바꾸는 방법을 알아보겠습니다.

 

1) 칼럼 지정해서 변경

df.loc[(cond_adult) & (cond_freq_under4),"Class"] = "해적"
df[(cond_adult) & (cond_freq_under4)]

* 코드 설명

조건으로 선택된 행의 값을 바꾸는 방법은 df.loc[조건,"컬럼이름"]= 바꿀 값입니다. 위 예시를 보면, df.loc[(cond_adult) & (cond_freq_under4),"Class"] = "해적"으로, Age가 Adult이고, Freq이 4 미만인 경우 "Class"칼럼의 값을 "해적"으로 바꾸겠다는 의미입니다. 값을 바꾸고, 잘 변경되었는지 출력해보겠습니다.

* 출력

조건에 따른 행 -> 컬럼 지정해서 값 변경

2) 행 전체 변경

df.loc[(cond_adult) & (cond_freq_under4)] = ["해적왕", "여자", "90", "Yes", 100]
df[(cond_adult) & (cond_freq_under4)]

* 코드 설명

행 전체를 바꾸는 방법은 f.loc[조건]= [행 바꿀 값 리스트]입니다. 이때, [행 바꿀 값 리스트]의 요소 개수가 df의 칼럼 개수와 동일하고, 데이터 타입도 일치해야 합니다. 위 코드에서 df.loc[(cond_adult) & (cond_freq_under4)] = ["해적왕", "여자", "90", "Yes", 100] 부분을 보겠습니다. df의 칼럼이 ['Class', 'Sex', 'Age', 'Survived', 'Freq'] 이기 때문에 각각에 맞게 ["해적왕", "여자", "90", "Yes", 100]으로 [문자열, 문자열, 문자열, 숫자형]으로 기존 데이터 타입에 맞게 주었습니다. 그러면 조건에 만족하는 행들이 모두 바뀌게 됩니다.

* 출력

조건에 따른 행 -> 행 전체 값 변경

 

4. 결론

판다스의 데이터 프레임에서 조건에 따라 행을 선택하고, 조건들을 &(and)나 |(or)로 합쳐보기도 하고, 선택된 행의 값을 바꿔보기도 했습니다. 이 연산들은 실제로 데이터 프레임을 다루다 보면 정말 많이 쓰입니다. 캐글 컴페티션 등의 노트북을 보면, 조건들을 변수에 넣고 이리저리 합쳐서 쓰는 경우를 많이 볼 수 있습니다. 위처럼 cond_로 시작하여 많이 사용합니다. 

 

읽어주셔서 감사합니다.

다음에 더 유익하고 재미있는 글로 찾아오겠습니다.

 

* 위의 실습 코드 깃허브를 공유드립니다. (주피터 노트북)

https://github.com/netsus/pandas_practice/blob/master/Pandas_select_row_with_condition.ipynb

 

GitHub - netsus/pandas_practice: Pandas examples in practice.

Pandas examples in practice. Contribute to netsus/pandas_practice development by creating an account on GitHub.

github.com

 

 

반응형

댓글

Designed by JB FACTORY