이번 포스팅에서는 데이터프레임을 그룹화하는 방법에 대해 알아보도록 하겠습니다.
import pandas as pd
1. GroupBy 객체
데이터프레임의 특정 컬럼을 기준으로 데이터셋을 그룹화해야 하는 경우가 있습니다.
이때 groupby 메서드를 사용해 데이터프레임을 그룹화할 수 있습니다.
그룹화의 결과로 DataFrameGroupBy 객체가 생성되는데 간단하게 GroupBy 객체라고 부르겠습니다.
GroupBy 객체는 데이터프레임 행을 버킷으로 그룹화하여 관리하는 저장소 컨테이너라고 볼 수 있습니다.
특정 컬럼이 공유하는 값을 기반으로 데이터프레임의 행을 버킷으로 구성한다고도 볼 수 있습니다.
쉽게 얘기해서 특정 컬럼의 값들을 기준으로 생겨난 각 그룹이 GroupBy 객체를 구성한다는 것입니다.
참고로 각 그룹은 또 다른 데이터프레임을 의미합니다.
이러한 GroupBy 객체는 데이터프레임을 분할, 재구성, 집계할 수 있는 최적의 자료구조입니다.
2. 데이터프레임 그룹화하기
위 그림은 이번 포스팅을 진행하며 예제로 다룰 fortune 데이터프레임입니다.
import pandas as pd
fortune = pd.read_csv('fortune1000.csv')
print(fortune.head())
fortune 데이터프레임의 Sector 컬럼을 기준으로 그룹화 했습니다.
len 함수를 통해 그룹화 결과로 생성된 그룹(데이터프레임)의 개수를 확인할 수 있습니다.
sectors = fortune.groupby('Sector')
# 아래 두 줄의 코드는 동일한 결과를 리턴합니다.
print(len(sectors)) # 21
print(fortune['Sector'].nunique()) # 21
3. GroupBy 객체의 속성과 메서드
3-1. 속성
✅ groups
각 그룹과 데이터프레임 레코드 사이의 관계를 확인할 수 있는 딕셔너리를 리턴합니다.
키는 그룹의 이름을, 값은 각 그룹에 속한 레코드들의 인덱스 값으로 구성된 Index 객체를 의미합니다.
다음 코드를 통해 'Apparel' 그룹에는 88, 241, ..., 997번재 레코드가 포함된다는 사실을 알 수 있습니다.
sectors.groups
3-2. 메서드
✅ size
그룹명과 각 그룹에 포함된 레코드의 개수로 구성된 Series를 리턴합니다.
sectors.size()
✅ first, last
first, last 메서드는 각 그룹별 첫번째/마지막 레코드로 구성된 데이터프레임을 리턴합니다.
아래 예제코드는 각 섹터별 첫 번째 기업들로 구성된 데이터프레임을 리턴합니다.
print(sectors.first())
print(len(sectors.first()))
# 21
✅ nth
각 그룹별 특정 인덱스 위치에 있는 레코드로 구성된 데이터프레임을 리턴합니다.
예를 들면 nth 메서드의 인수로 0을 전달하면 각 섹터별 첫 번째 기업들로 구성된 데이터프레임을 리턴합니다.
아래 두 예제코드는 동일한 결과를 반환합니다.
# 1) first 메서드
sectors.first()
# 2) nth 메서드
sectors.nth(0)
✅ head, tail
head, tail 메서드는 각 그룹별 처음/마지막 n개의 레코드로 구성된 데이터프레임을 리턴합니다.
다음 예제코드는 각 그룹별 처음 2개의 레코드들로 구성된 데이터프레임을 반환합니다.
그룹의 개수가 총 21개이기 때문에 리턴되는 데이터프레임의 길이는 42입니다.
sectors.head(2)
print(len(sectors.head(2)))
# 42
✅ get_group
특정 그룹의 모든 레코드들로 구성된 데이터프레임을 리턴합니다.
아래 예제 코드는 Energy 그룹에 속한 모든 기업 데이터들을 담은 데이터프레임을 반환합니다.
sectors.get_group('Energy')
4. GroupBy 객체의 집계 연산
집계 연산 메서드를 활용하면 각 그룹별로 연산을 수행할 수 있습니다.
✅ sum
다음 예제코드는 각 그룹별 Revenues, Profits, Employees 컬럼에 대해 합계를 계산한 결과를 데이터프레임으로 리턴합니다.
sectors.sum(['Revenues', 'Profits', 'Employees'])
✅ mean
아래 예제코드는 각 그룹별 Revenues, Profits, Employees 컬럼에 대해 평균을 계산한 결과를 데이터프레임으로 리턴합니다.
sectors.mean(['Revenues', 'Profits', 'Employees'])
✅ 대괄호 연산
대괄호를 사용하면 각 그룹별 특정 컬럼에 접근할 수 있습니다.
다음 예제코드는 각 그룹에 속한 기업들의 매출(Revenues)의 총합을 Series로 리턴합니다.
sectors['Revenues'].sum()
✅ min, max
min(최소값), max(최대값) 메서드는 앞서 살펴본 대괄호와 함께 사용할 수 있습니다.
다음 예제코드는 각 그룹별 가장 높은 이익(Profits)을 본 기업의 이익 데이터를 Series로 리턴합니다.
sectors['Profits'].max()
✅ agg
agg 메서드를 사용하면 서로 다른 집계 연산을 각 컬럼에 적용할 수 있습니다.
인수로 딕셔너리를 전달 받고 데이터프레임을 리턴합니다.
다음 예제코드는 각 그룹의 Revenues 컬럼에 min 메서드를, Profits 컬럼에는 max 메서드를, Employees 컬럼에는 mean 메서드를 적용한 결과를 데이터프레임으로 반환합니다.
aggregations = {
"Revenues": "min",
"Profits": "max",
"Employees": "mean"
}
sectors.agg(aggregations)
마치며
이상으로 데이터프레임을 그룹화하는 방법에 대한 정리를 마치도록 하겠습니다.
groupby와 pivot_table 메서드를 통해 데이터 전처리에 보다 더 능숙해져야겠습니다.
'데이터 분석 > pandas' 카테고리의 다른 글
판다스 datetime 요일로 변환하기 (0) | 2023.07.18 |
---|