Data_10기

Python Standard - melt, stack, unstack

senu 2025. 12. 2. 21:13

오늘은 새로운 조 편성과 분반 조정 이후 처음 듣는 수업이라 그런지 조금 기분이 묘한 상태로 수업을 듣게 되었다. 이전 시간에 배운 Transpose와 Pivot table을 복습한 다음, 데이터 변형에서 쏠쏠하게 쓰일 수 있는 Melt, Stack, Unstack에 대해 배울 수 있었다.


Ⅰ. 복습 (Transpose, Pivot Table)

1. Transpose

데이터의 열과 행을 바꿔주는 전치함수로, 열이 많을 경우 간단한 행렬전환을 통해 구조를 살펴볼 수 있게 해주는 메소드이다.

데이터 크기가 큰 경우, 시간이 오래 걸릴 수 있어 행렬전환 이전에, head() 등으로 전체 데이터를 잘라준 다음 구조를 파악해주면 된다.

# 기본 문법
데이터프레임명.T

 

2. Pivot Table

Pivot Table은 Index, Columns, Values, Aggfunc 을 직접 선언하여 테이블을 변환하는 함수로, 특정 열을 기준으로 데이터를 요약하고, 새로운 형태의 표로 변환해주는 메소드이다.

※ columns 를 제외한 나머지(index, values, aggfunc)는 필수 파라미터이다.

# 기본 문법
pd.pivot_table(데이터프레임명, index=컬럼명, columns=컬럼명, values=컬럼명, aggfunc=연산방식)
  • index : 인덱스(축)으로 사용될 열
  • columns : 열로 사용될 열
  • values : 값으로 사용될 열
  • aggfunc : 연산 방식 (sum, mean, std, count, nunique, max, min)

 

Index, Values, aggfunc 에 여러개의 컬럼명을 입력하고 싶을 경우, list 형식으로 지정할 수 있다.

  • index 와 columns 를 list 형식으로 입력 → 멀티 인덱스 기반 피벗테이블 생성할 수 있음
  • values 를 list 형식으로 입력 → 각 연산을 포함한 피벗테이블 생성

Ⅱ. Melt, Stack, Unstack

본격적인 메소드 정리에 앞서 wide format과 long format에 대해 먼저 정리해보겠다.

 

Wide Format

- 각 주제 또는 관찰 단위가 단일 행으로 표시되는 구조

- 즉, 관찰단위를 dintinct하게 봄

- 측정값을 모두 한 행에 표시하고, 열이름으로 그 측정값의 의미를 나타낸 형태

 

Long Format

- 하나의 열에 데이터를 나타내고 다른 열에 데이터에 대응하는 변수를 나타낸 형태

- 데이터를 기록할 때 하나의 관찰값(예: 행)이 하나의 행에 위치하도록 하는 형태

 

1. Melt

Melt는 데이터프레임의 컬럼을 열로 바꿔주는 메소드로, wide format에서 long format으로 데이터프레임을 변형해주는 역할을 한다. 즉, 피벗 형태의 테이블을 기존 형태로 바꿔줄 때 사용된다.

# 기본 문법
데이터프레임명.melt(
	      id_vars=None,
              value_vars=None, 
              var_name=None, 
              value_name='value', 
              col_level=None, 
              ignore_index=True
)
  • id_vars : 기준이 될 열 (그대로 유지할 열)
  • value_vars : 기준열에 대한 하위 카테고리를 나열할 열 선택 (병합할 열)
  • var_name : 카테고리들이 나열된 열의 이름 설정 (병합 후 표현할 열 이름)
  • value_name : 카테고리들의 값이 나열될 열의 이름 설정 (기본값 : value)
  • col_level : multi index의 경우 melt를 수행할 레벨을 설정
  • ignore_index : 인덱스를 1, 2, 3, ... , n으로 설정할지 여부 (기본값 : True => 1, 2, 3, ..., n으로 설정)

 

Melt 실습 1)

# melt
df2 = pd.read_csv("customer_details.csv") # customer_details.csv

df_melted = df2.melt(
    id_vars=['Customer ID'],
    value_vars=['Size', 'Season'],
    var_name='Feature',
    value_name='Value'
)

 

2. Stack

컬럼을 인덱스의 하위 레벨로 변환하는 메소드로, 멀티인덱스 처리가 가능하다.

# 기본 문법
데이터프레임명.stack(level=-1, dropna=True)
  • level : stack을 수행할 인덱스 레벨 지정하는 옵션
  • dropna : stack을 수행한 결과에서 결측값을 제거할지 여부 지정하는 옵션 (기본값 : True => 결측값 제거)

 

Stack 실습)

# stack 
df2 = pd.read_csv("customer_details.csv") # customer_details.csv

# 필요한 컬럼 선택 (시리즈 형태로 가져올거니까 대괄호 두 개 사용해서 슬라이싱함)
df22 = df2[['Category', 'Season', 'Purchase Amount (USD)', 'Review Rating']].copy()

# pd.MultiIndex from tuples 를 통해, 멀티인덱스 설정 ***
df22.columns = pd.MultiIndex.from_tuples([('Purchase', 'Amount'), ('Purchase', 'Review'),
                                              ('Info', 'Category'), ('Info', 'Season')])

# stack(level=0) 적용
df_stacked_0 = df22.stack(level=0)

# stack(level=1) 적용
df_stacked_1 = df22.stack(level=1)

# 결과 비교 
# 원본데이터, stack0 데이터, stack1 데이터 
display(df22, df_stacked_0, df_stacked_1)

df22(왼쪽), df_stacked_0(중앙), df_stacked_1(오른쪽)

 

3. Unstack

Unstack 은 인덱스 레벨을 컬럼으로 변환하는 메소드로, stack과 마찬가지로 멀티인덱스 처리가 가능하다.

# 기본 문법
데이터프레임명.unstack(level=-1, fill_value=None)
  • level : unstack을 수행할 인덱스 레벨을 지정하는 옵션
  • fill_value : unstack을 수행한 결과에서 결측값을 채울 값을 지정하는 옵션 (기본값 : None => 결측값을 그대로 둠)

 

Unstack 실습)

# unstack(level=-1) 적용. 기본값
df_unstacked_0 = df_stacked_0.unstack(-1).reset_index()

# 결과 비교 
# 원본데이터, stack 데이터, unstack 데이터
# df_stacked_0 = df22.stack(level=0) 
display(df22, df_stacked_0, df_unstacked_0)

df22(왼쪽), df_stacked_0(중앙), df_unstacked_0(오른쪽)


마무리

오늘 라이브 세션에서는 데이터 구조를 필요에 맞게 변형할 수 있는 방법들을 배울 수 있었다. 분반을 시작하면서 반 이름이 주는 무게감에 조금 긴장을 했었지만 놓친 부분 없이 잘 따라간 것 같아 다행인 것 같다. 다만 수업 중에 SQL window function 같이 배운지 시간이 좀 지난 내용에 대해서는 기억이 흐릿해져서 복습이 필요하다고 느꼈다. 오늘처럼 복습이 필요한 부분을 하나씩 체크하면서 새로운 함수도 익힐 수 있게 계획을 잘 세워봐야겠다.