본문 바로가기
파이썬(Python)

파이썬-데이터프레임 변환 melt, pivot 함수 사용하기

by 즐거운코딩 2025. 8. 17.
반응형

보통 원본 데이터는 사람이 보기 좋게 "가로로 넓게(wide)" 되어 있는데, 분석 라이브러리(pandas groupby, seaborn, matplotlib, pivot_table) 등은 "세로(long)" 구조일 때 더 다루기 편리합니다.

 

다음의 예시의 경우 melt() 함수를 이용하여 쉽게 분석작업이 가능합니다.

 

1.  melt() 사용이 유리한 상황 예시

1️⃣ 월별 데이터를 시각화할 때

df = pd.DataFrame({
    "지역": ["서울", "부산", "대구"],
    "1월": [100, 150, 120],
    "2월": [200, 250, 300],
    "3월": [130, 180, 160]
})
  • 현재 구조: wide
  • 문제점: matplotlib이나 seaborn으로 월을 x축에, 매출을 y축에 두려면 불편

👉 melt() 변환:

df_melt = pd.melt(df, id_vars="지역", var_name="월", value_name="매출")

결과:

    지역   월   매출
0   서울  1월  100
1   부산  1월  150
2   대구  1월  120
3   서울  2월  200
...

→ 이렇게 변환하면 바로

import seaborn as sns
sns.barplot(data=df_melt, x="월", y="매출", hue="지역")

📊 한 줄로 그래프를 그릴 수 있음.


2️⃣ groupby / pivot_table 같은 집계 분석할 때

원래 wide 형태에서는 sum, mean 계산이 월 단위로 어렵습니다.
melt 후에는 groupby만 쓰면 간단합니다:

df_melt.groupby(["월"])["매출"].sum()

→ 각 월별 매출 합계 바로 구해짐.


3️⃣ 머신러닝 모델 입력 데이터 준비할 때

  • 모델 학습용 데이터는 보통 세로(long) 구조를 선호
  • 예: 시간별 센서 데이터, 설문 응답(각 항목별 점수), 시험 점수

원본 데이터 (wide):

학생    수학   영어   과학
철수    80    70    90
영희    85    95    88

melt 후 (long):

학생   과목    점수
철수   수학    80
철수   영어    70
철수   과학    90
영희   수학    85
영희   영어    95
영희   과학    88

👉 이렇게 변환하면 과목별 분석, 특정 과목만 추출, 평균 점수 계산 등 데이터 가공이 쉬워짐.


4️⃣ 여러 sheet / 여러 항목을 한 번에 합치고 싶을 때

  • 병원 진료 데이터, 매장별 판매 데이터, 센서별 측정값 등은 보통 wide
  • melt() 하면 **"측정항목 이름" + "측정값"**으로 정리되어서 여러 시트/테이블을 쉽게 합칠 수 있음.

🔑 요약

  • melt()는 사람이 읽기 좋은 wide → 기계/분석용 long 변환
  • 그래프 그리기, groupby 집계, 머신러닝 feature 정리 등에 반드시 필요

2.  melt() 사용 예시


melt() 함수는 wide 형식 데이터를 long 형식으로 변환할 때 사용합니다.
즉, 여러 개의 컬럼을 하나로 모아 "값" 컬럼으로 만들고, 어떤 컬럼에서 왔는지 표시하는 "변수" 컬럼을 추가하는 방식입니다.


1️⃣ 기본 예시

샘플 데이터:

import pandas as pd

df = pd.DataFrame({
    "지역": ["서울", "부산", "대구"],
    "1월": [100, 150, 120],
    "2월": [200, 250, 300],
    "3월": [130, 180, 160]
})

print(df)

출력:

    지역   1월   2월   3월
0   서울  100  200  130
1   부산  150  250  180
2   대구  120  300  160

👉 melt() 변환

df_melted = pd.melt(df, 
                    id_vars=["지역"],   # 고정할 열
                    var_name="월",     # 녹아내린 컬럼 이름
                    value_name="매출") # 값 컬럼 이름

print(df_melted)

결과:

    지역   월   매출
0   서울  1월  100
1   부산  1월  150
2   대구  1월  120
3   서울  2월  200
4   부산  2월  250
5   대구  2월  300
6   서울  3월  130
7   부산  3월  180
8   대구  3월  160

👉 wide → long 변환 완료!
이제 지역, 월 기준으로 pivot_table 같은 분석이 가능해집니다.


2️⃣ 여러 id_vars 유지

id_vars에 여러 개 컬럼을 지정할 수 있습니다.

예시 데이터:

df2 = pd.DataFrame({
    "지역": ["서울", "부산", "대구"],
    "담당자": ["김철수", "이영희", "박민수"],
    "1월": [100, 150, 120],
    "2월": [200, 250, 300]
})

df2_melted = pd.melt(df2, 
                     id_vars=["지역", "담당자"], 
                     var_name="월", 
                     value_name="매출")

print(df2_melted)

결과:

    지역   담당자   월   매출
0   서울  김철수  1월  100
1   부산  이영희  1월  150
2   대구  박민수  1월  120
3   서울  김철수  2월  200
4   부산  이영희  2월  250
5   대구  박민수  2월  300

3️⃣ 특정 컬럼만 melt

# 1월과 2월만 long 형식으로 변환
df_partial = pd.melt(df, 
                     id_vars=["지역"], 
                     value_vars=["1월", "2월"], 
                     var_name="월", 
                     value_name="매출")

print(df_partial)

결과:

    지역   월   매출
0   서울  1월  100
1   부산  1월  150
2   대구  1월  120
3   서울  2월  200
4   부산  2월  250
5   대구  2월  300

✅ 정리

  • id_vars → 고정할 컬럼
  • value_vars → long으로 녹일 컬럼 (생략하면 나머지 전부)
  • var_name, value_name → 새로 생길 열 이름 지정

 

3.  melt() → pivot() 되돌리기

 

👍  바로 실무에서 자주 쓰는 melt() → pivot() 되돌리기 과정을 예제입니다.


📌 1. 원본 데이터 (Wide 형태)

예를 들어 매출 데이터가 이렇게 있다고 합시다:

import pandas as pd

df = pd.DataFrame({
    "지역": ["서울", "부산", "대구"],
    "1월": [100, 150, 120],
    "2월": [200, 250, 300],
    "3월": [130, 180, 160]
})

print(df)

출력:

    지역   1월   2월   3월
0   서울  100  200  130
1   부산  150  250  180
2   대구  120  300  160

📌 2. melt() 변환 (Wide → Long)

월을 세로로 녹여서 long 형태로 바꿉니다:

df_melt = pd.melt(
    df,
    id_vars="지역",        # 기준 열 (그대로 유지)
    var_name="월",        # 녹여서 새로 만들 열 이름
    value_name="매출"     # 값 열 이름
)

print(df_melt)

출력:

    지역   월   매출
0   서울  1월  100
1   부산  1월  150
2   대구  1월  120
3   서울  2월  200
4   부산  2월  250
5   대구  2월  300
6   서울  3월  130
7   부산  3월  180
8   대구  3월  160

👉 이제 월을 x축, 매출을 y축으로 바로 그래프 그릴 수 있음.


📌 3. pivot()으로 되돌리기 (Long → Wide)

이제 다시 원래 wide 형태로 되돌려봅니다:

df_pivot = df_melt.pivot(
    index="지역",   # 행으로 둘 열
    columns="월",   # 열로 펼칠 항목
    values="매출"   # 값
).reset_index()

print(df_pivot)

출력:

월   지역   1월   2월   3월
0   대구  120  300  160
1   부산  150  250  180
2   서울  100  200  130

👉 원본과 거의 동일한 구조로 복원됨. (행 순서가 바뀔 수 있음 → sort_index() 하면 정렬 가능)


📌 4. 실무에서 중요한 점

  • melt() → pivot()은 기본적으로 상호 역변환이지만,
  • 중복값이 있으면 pivot()에서 에러가 발생.

예:

지역=서울, 월=1월 → 값이 두 개 이상 있으면 pivot 불가

👉 이런 경우 pivot_table()을 쓰고 aggfunc='sum' 같은 집계를 지정해야 합니다.

df_pivot_table = df_melt.pivot_table(
    index="지역",
    columns="월",
    values="매출",
    aggfunc="sum",    # 중복이 있을 때는 합계로 처리
    fill_value=0      # NaN 대신 0으로 채우기
).reset_index()

✅ 요약

  • melt(): Wide → Long 변환 (분석/시각화/모델링에 적합)
  • pivot(): Long → Wide 복원
  • pivot_table(): 중복값 처리 및 집계 기능 포함
반응형