Visualización de Datos 📊
데이터 시각화는 복잡한 데이터를 이해하기 쉬운 그래픽으로 표현하는 과정입니다. Matplotlib은 파이썬에서 가장 널리 사용되는 시각화 라이브러리입니다.
¿Qué es Matplotlib?
Matplotlib은 파이썬에서 2D 그래프와 차트를 그리는 라이브러리입니다. MATLAB과 유사한 인터페이스를 제공합니다.
Características Principales
- 다양한 차트: 선, 막대, 산점도, 히스토그램 등
- 커스터마이징: 세밀한 스타일 조정 가능
- Pandas 통합: DataFrame과 쉽게 연동
- 출판 품질: 논문/보고서용 그래프 생성
Instalación
pip install matplotlib
import matplotlib.pyplot as plt
import numpy as np
# 한글 폰트 설정 (macOS)
plt.rcParams['font.family'] = 'AppleGothic'
# Windows: 'Malgun Gothic'
# Linux: 'NanumGothic'
# 마이너스 기호 깨짐 방지
plt.rcParams['axes.unicode_minus'] = False
print(f"Matplotlib 버전: {plt.__version__}")
Gráficos Básicos
Gráfico de Líneas (Line Plot)
import matplotlib.pyplot as plt
import numpy as np
# 데이터 준비
x = np.linspace(0, 10, 100)
y = np.sin(x)
# 그래프 그리기
plt.plot(x, y)
plt.title('사인 함수')
plt.xlabel('x')
plt.ylabel('sin(x)')
plt.grid(True)
plt.show()
# 여러 선 그리기
plt.figure(figsize=(10, 6))
plt.plot(x, np.sin(x), label='sin(x)')
plt.plot(x, np.cos(x), label='cos(x)')
plt.title('삼각함수')
plt.xlabel('x')
plt.ylabel('y')
plt.legend()
plt.grid(True)
plt.show()
스타일 옵션
x = np.linspace(0, 10, 20)
y = x ** 2
# 선 스타일
plt.plot(x, y, 'r--', linewidth=2) # 빨간 점선
plt.plot(x, y, 'bo-', markersize=8) # 파란 동그라미와 선
plt.plot(x, y, 'g^:', alpha=0.5) # 초록 삼각형과 점선 (반투명)
# 더 명시적으로
plt.plot(x, y,
color='blue', # 색상
linestyle='--', # 선 스타일
linewidth=2, # 선 두께
marker='o', # 마커 모양
markersize=8, # 마커 크기
markerfacecolor='red', # 마커 내부 색
markeredgecolor='black',# 마커 테두리 색
alpha=0.7, # 투명도
label='데이터' # 범례
)
Gráfico de Barras (Bar Chart)
수직 막대 그래프
import matplotlib.pyplot as plt
# 데이터
categories = ['A', 'B', 'C', 'D', 'E']
values = [23, 45, 56, 78, 32]
# Gráfico de Barras
plt.figure(figsize=(10, 6))
plt.bar(categories, values, color='skyblue', edgecolor='black')
plt.title('제품별 판매량')
plt.xlabel('제품')
plt.ylabel('판매량')
plt.grid(axis='y', alpha=0.3)
plt.show()
# 색상 다르게
colors = ['red', 'green', 'blue', 'orange', 'purple']
plt.bar(categories, values, color=colors)
plt.show()
수평 막대 그래프
# 수평 막대
plt.figure(figsize=(10, 6))
plt.barh(categories, values, color='lightcoral')
plt.title('제품별 판매량')
plt.xlabel('판매량')
plt.ylabel('제품')
plt.show()
그룹 막대 그래프
import numpy as np
# 데이터
categories = ['A', 'B', 'C', 'D']
values1 = [23, 45, 56, 78]
values2 = [34, 55, 48, 70]
x = np.arange(len(categories))
width = 0.35
# 그룹 막대
fig, ax = plt.subplots(figsize=(10, 6))
ax.bar(x - width/2, values1, width, label='2023년', color='skyblue')
ax.bar(x + width/2, values2, width, label='2024년', color='lightcoral')
ax.set_xlabel('제품')
ax.set_ylabel('판매량')
ax.set_title('연도별 제품 판매 비교')
ax.set_xticks(x)
ax.set_xticklabels(categories)
ax.legend()
ax.grid(axis='y', alpha=0.3)
plt.tight_layout()
plt.show()
누적 막대 그래프
# 누적 막대
categories = ['Q1', 'Q2', 'Q3', 'Q4']
product_a = [20, 35, 30, 35]
product_b = [25, 32, 34, 20]
product_c = [15, 20, 25, 30]
plt.figure(figsize=(10, 6))
plt.bar(categories, product_a, label='제품 A')
plt.bar(categories, product_b, bottom=product_a, label='제품 B')
plt.bar(categories, product_c, bottom=np.array(product_a)+np.array(product_b), label='제품 C')
plt.xlabel('분기')
plt.ylabel('판매량')
plt.title('분기별 제품 판매')
plt.legend()
plt.show()
Diagrama de Dispersión (Scatter Plot)
import matplotlib.pyplot as plt
import numpy as np
# 데이터
np.random.seed(42)
x = np.random.rand(100) * 100
y = np.random.rand(100) * 100
sizes = np.random.rand(100) * 100
colors = np.random.rand(100)
# 기본 산점도
plt.figure(figsize=(10, 6))
plt.scatter(x, y)
plt.title('기본 산점도')
plt.xlabel('X')
plt.ylabel('Y')
plt.grid(True, alpha=0.3)
plt.show()
# 크기와 색상 적용
plt.figure(figsize=(10, 6))
scatter = plt.scatter(x, y, s=sizes, c=colors, cmap='viridis', alpha=0.6)
plt.colorbar(scatter, label='값')
plt.title('크기와 색상을 가진 산점도')
plt.xlabel('X')
plt.ylabel('Y')
plt.grid(True, alpha=0.3)
plt.show()
상관관계 시각화
# 키와 몸무게 상관관계
height = np.random.normal(170, 10, 100)
weight = height * 0.8 + np.random.normal(0, 5, 100)
plt.figure(figsize=(10, 6))
plt.scatter(height, weight, alpha=0.5)
plt.title('키와 몸무게 상관관계')
plt.xlabel('키 (cm)')
plt.ylabel('몸무게 (kg)')
# 추세선 추가
z = np.polyfit(height, weight, 1)
p = np.poly1d(z)
plt.plot(height, p(height), "r--", alpha=0.8, label='추세선')
plt.legend()
plt.grid(True, alpha=0.3)
plt.show()
Histograma (Histogram)
import matplotlib.pyplot as plt
import numpy as np
# 정규분포 데이터
data = np.random.normal(100, 15, 1000)
# Histograma
plt.figure(figsize=(10, 6))
plt.hist(data, bins=30, color='skyblue', edgecolor='black', alpha=0.7)
plt.title('시험 점수 분포')
plt.xlabel('점수')
plt.ylabel('빈도')
plt.axvline(data.mean(), color='red', linestyle='--', linewidth=2, label=f'평균: {data.mean():.1f}')
plt.legend()
plt.grid(axis='y', alpha=0.3)
plt.show()
# 여러 히스토그램 비교
data1 = np.random.normal(100, 15, 1000)
data2 = np.random.normal(110, 10, 1000)
plt.figure(figsize=(10, 6))
plt.hist(data1, bins=30, alpha=0.5, label='A반', color='blue')
plt.hist(data2, bins=30, alpha=0.5, label='B반', color='red')
plt.title('반별 시험 점수 분포')
plt.xlabel('점수')
plt.ylabel('빈도')
plt.legend()
plt.grid(axis='y', alpha=0.3)
plt.show()
Gráfico de Pastel (Pie Chart)
# 데이터
labels = ['Python', 'Java', 'JavaScript', 'C++', 'Others']
sizes = [35, 25, 20, 10, 10]
colors = ['#ff9999', '#66b3ff', '#99ff99', '#ffcc99', '#ff99cc']
explode = (0.1, 0, 0, 0, 0) # Python 강조
# Gráfico de Pastel
plt.figure(figsize=(10, 8))
plt.pie(sizes, explode=explode, labels=labels, colors=colors,
autopct='%1.1f%%', shadow=True, startangle=90)
plt.title('프로그래밍 언어 사용 비율')
plt.axis('equal')
plt.show()
# 도넛 차트
plt.figure(figsize=(10, 8))
plt.pie(sizes, labels=labels, colors=colors,
autopct='%1.1f%%', startangle=90,
wedgeprops={'width': 0.5}) # 도넛 모양
plt.title('프로그래밍 언어 사용 비율 (도넛)')
plt.axis('equal')
plt.show()
Diagrama de Caja (Box Plot)
import numpy as np
# 데이터
np.random.seed(42)
data1 = np.random.normal(100, 10, 200)
data2 = np.random.normal(90, 15, 200)
data3 = np.random.normal(110, 5, 200)
# Diagrama de Caja
plt.figure(figsize=(10, 6))
plt.boxplot([data1, data2, data3],
labels=['A반', 'B반', 'C반'],
patch_artist=True,
boxprops=dict(facecolor='lightblue', alpha=0.5),
medianprops=dict(color='red', linewidth=2))
plt.title('반별 시험 점수 분포')
plt.ylabel('점수')
plt.grid(axis='y', alpha=0.3)
plt.show()
Subgráficos (Subplots)
기본 서브플롯
# 2x2 서브플롯
fig, axes = plt.subplots(2, 2, figsize=(12, 10))
# 왼쪽 위: 선 그래프
x = np.linspace(0, 10, 100)
axes[0, 0].plot(x, np.sin(x))
axes[0, 0].set_title('선 그래프')
axes[0, 0].grid(True)
# 오른쪽 위: 막대 그래프
categories = ['A', 'B', 'C', 'D']
values = [23, 45, 56, 78]
axes[0, 1].bar(categories, values, color='skyblue')
axes[0, 1].set_title('막대 그래프')
# 왼쪽 아래: 산점도
x = np.random.rand(50)
y = np.random.rand(50)
axes[1, 0].scatter(x, y, alpha=0.5)
axes[1, 0].set_title('산점도')
# 오른쪽 아래: 히스토그램
data = np.random.normal(0, 1, 1000)
axes[1, 1].hist(data, bins=30, color='lightcoral')
axes[1, 1].set_title('히스토그램')
plt.tight_layout()
plt.show()
다양한 레이아웃
# 불균등한 서브플롯
fig = plt.figure(figsize=(12, 8))
# 2x2 그리드에서 다양한 크기
ax1 = plt.subplot(2, 2, 1)
ax1.plot([1, 2, 3], [1, 4, 9])
ax1.set_title('Plot 1')
ax2 = plt.subplot(2, 2, 2)
ax2.bar(['A', 'B', 'C'], [10, 20, 15])
ax2.set_title('Plot 2')
ax3 = plt.subplot(2, 1, 2) # 아래쪽 전체
ax3.plot(np.random.rand(100))
ax3.set_title('Plot 3 (Wide)')
plt.tight_layout()
plt.show()
Estilización
기본 스타일
# 사용 가능한 스타일 확인
print(plt.style.available)
# 스타일 적용
plt.style.use('seaborn-v0_8-darkgrid')
# 또는 'ggplot', 'fivethirtyeight', 'bmh' 등
x = np.linspace(0, 10, 100)
y = np.sin(x)
plt.figure(figsize=(10, 6))
plt.plot(x, y, linewidth=2)
plt.title('스타일이 적용된 그래프')
plt.show()
# 스타일 초기화
plt.style.use('default')
색상 선택
# 다양한 색상 지정 방법
plt.plot(x, y, color='red') # 이름
plt.plot(x, y, color='r') # 약자
plt.plot(x, y, color='#FF5733') # Hex 코드
plt.plot(x, y, color=(0.1, 0.2, 0.5)) # RGB 튜플
plt.plot(x, y, color=(0.1, 0.2, 0.5, 0.7)) # RGBA (투명도 포함)
# 컬러맵 사용
colors = plt.cm.viridis(np.linspace(0, 1, 10))
for i in range(10):
plt.plot(x, y + i, color=colors[i])
폰트와 텍스트
plt.figure(figsize=(10, 6))
# 타이틀
plt.title('제목', fontsize=20, fontweight='bold', color='navy')
# 축 레이블
plt.xlabel('X축', fontsize=14, style='italic')
plt.ylabel('Y축', fontsize=14, style='italic')
# 텍스트 추가
plt.text(5, 0.5, '주석 텍스트', fontsize=12,
bbox=dict(boxstyle='round', facecolor='wheat', alpha=0.5))
# 화살표와 주석
plt.annotate('중요 지점', xy=(7, 0.7), xytext=(8, 0.9),
arrowprops=dict(arrowstyle='->', color='red', lw=2),
fontsize=12)
plt.plot(x, y)
plt.show()
Ejemplos Prácticos
예제 1: 월별 매출 대시보드
import matplotlib.pyplot as plt
import numpy as np
import pandas as pd
# 데이터 생성
months = ['1월', '2월', '3월', '4월', '5월', '6월']
sales_2023 = [120, 135, 148, 162, 155, 178]
sales_2024 = [145, 158, 170, 185, 192, 205]
target = [150] * 6
# 대시보드 생성
fig = plt.figure(figsize=(16, 10))
fig.suptitle('2024년 상반기 매출 분석 대시보드', fontsize=20, fontweight='bold')
# 1. 월별 매출 비교 (선 그래프)
ax1 = plt.subplot(2, 3, 1)
ax1.plot(months, sales_2023, marker='o', linewidth=2, label='2023년', color='skyblue')
ax1.plot(months, sales_2024, marker='s', linewidth=2, label='2024년', color='coral')
ax1.plot(months, target, linestyle='--', linewidth=2, label='목표', color='green')
ax1.set_title('월별 매출 추이', fontsize=14, fontweight='bold')
ax1.set_ylabel('매출 (백만원)')
ax1.legend()
ax1.grid(True, alpha=0.3)
# 2. 연도별 총 매출 (막대 그래프)
ax2 = plt.subplot(2, 3, 2)
total_sales = [sum(sales_2023), sum(sales_2024)]
colors = ['skyblue', 'coral']
bars = ax2.bar(['2023년', '2024년'], total_sales, color=colors, edgecolor='black', linewidth=2)
ax2.set_title('연도별 총 매출', fontsize=14, fontweight='bold')
ax2.set_ylabel('매출 (백만원)')
for bar in bars:
height = bar.get_height()
ax2.text(bar.get_x() + bar.get_width()/2., height,
f'{int(height)}M', ha='center', va='bottom', fontsize=12, fontweight='bold')
ax2.grid(axis='y', alpha=0.3)
# 3. 증감율 (막대 그래프)
ax3 = plt.subplot(2, 3, 3)
growth = [(s24 - s23) / s23 * 100 for s23, s24 in zip(sales_2023, sales_2024)]
colors_growth = ['green' if g > 0 else 'red' for g in growth]
ax3.bar(months, growth, color=colors_growth, alpha=0.7, edgecolor='black')
ax3.axhline(y=0, color='black', linestyle='-', linewidth=0.5)
ax3.set_title('전년 대비 증감율', fontsize=14, fontweight='bold')
ax3.set_ylabel('증감율 (%)')
ax3.grid(axis='y', alpha=0.3)
# 4. 목표 달성률 (수평 막대)
ax4 = plt.subplot(2, 3, 4)
achievement = [s / t * 100 for s, t in zip(sales_2024, target)]
colors_achievement = ['green' if a >= 100 else 'orange' for a in achievement]
ax4.barh(months, achievement, color=colors_achievement, alpha=0.7, edgecolor='black')
ax4.axvline(x=100, color='red', linestyle='--', linewidth=2, label='목표선')
ax4.set_title('월별 목표 달성률', fontsize=14, fontweight='bold')
ax4.set_xlabel('달성률 (%)')
ax4.legend()
ax4.grid(axis='x', alpha=0.3)
# 5. 매출 분포 (히스토그램)
ax5 = plt.subplot(2, 3, 5)
all_sales = sales_2023 + sales_2024
ax5.hist(all_sales, bins=10, color='mediumpurple', edgecolor='black', alpha=0.7)
ax5.axvline(np.mean(all_sales), color='red', linestyle='--',
linewidth=2, label=f'평균: {np.mean(all_sales):.1f}M')
ax5.set_title('매출 분포', fontsize=14, fontweight='bold')
ax5.set_xlabel('매출 (백만원)')
ax5.set_ylabel('빈도')
ax5.legend()
ax5.grid(axis='y', alpha=0.3)
# 6. 통계 요약 (텍스트)
ax6 = plt.subplot(2, 3, 6)
ax6.axis('off')
stats_text = f"""
📊 주요 지표 요약
2024년 총 매출: {sum(sales_2024):,}백만원
2023년 총 매출: {sum(sales_2023):,}백만원
증감: +{sum(sales_2024) - sum(sales_2023):,}백만원
증감율: +{(sum(sales_2024) - sum(sales_2023)) / sum(sales_2023) * 100:.1f}%
월평균 매출: {np.mean(sales_2024):.1f}백만원
최고 매출: {max(sales_2024)}백만원 ({months[sales_2024.index(max(sales_2024))]})
최저 매출: {min(sales_2024)}백만원 ({months[sales_2024.index(min(sales_2024))]})
목표 달성 월수: {sum(1 for s in sales_2024 if s >= 150)}/6개월
평균 달성률: {np.mean(achievement):.1f}%
"""
ax6.text(0.1, 0.5, stats_text, fontsize=12, verticalalignment='center',
fontfamily='monospace',
bbox=dict(boxstyle='round', facecolor='wheat', alpha=0.3))
plt.tight_layout()
plt.show()
예제 2: 제품 판매 분석
import matplotlib.pyplot as plt
import pandas as pd
# 제품 판매 데이터
data = {
'제품': ['노트북', '마우스', '키보드', '모니터', '헤드셋'],
'판매량': [450, 1200, 800, 350, 600],
'매출': [450000, 36000, 80000, 350000, 180000],
'재고': [120, 450, 280, 90, 200]
}
df = pd.DataFrame(data)
# 대시보드
fig, axes = plt.subplots(2, 2, figsize=(14, 10))
fig.suptitle('제품 판매 현황', fontsize=18, fontweight='bold')
# 1. 제품별 판매량
axes[0, 0].bar(df['제품'], df['판매량'], color='steelblue', edgecolor='black')
axes[0, 0].set_title('제품별 판매량', fontsize=14, fontweight='bold')
axes[0, 0].set_ylabel('판매량')
axes[0, 0].tick_params(axis='x', rotation=45)
axes[0, 0].grid(axis='y', alpha=0.3)
# 2. 제품별 매출
colors = plt.cm.Set3(range(len(df)))
axes[0, 1].barh(df['제품'], df['매출'], color=colors, edgecolor='black')
axes[0, 1].set_title('제품별 매출', fontsize=14, fontweight='bold')
axes[0, 1].set_xlabel('매출 (원)')
for i, v in enumerate(df['매출']):
axes[0, 1].text(v, i, f' {v:,}', va='center', fontsize=10)
axes[0, 1].grid(axis='x', alpha=0.3)
# 3. 매출 비율 (파이 차트)
explode = [0.05] * len(df)
explode[df['매출'].idxmax()] = 0.15 # 최대 매출 제품 강조
axes[1, 0].pie(df['매출'], labels=df['제품'], autopct='%1.1f%%',
explode=explode, shadow=True, startangle=90)
axes[1, 0].set_title('매출 비율', fontsize=14, fontweight='bold')
# 4. 판매량 vs 재고 (산점도)
axes[1, 1].scatter(df['판매량'], df['재고'], s=df['매출']/500,
c=range(len(df)), cmap='viridis', alpha=0.6, edgecolors='black', linewidth=2)
for i, txt in enumerate(df['제품']):
axes[1, 1].annotate(txt, (df['판매량'][i], df['재고'][i]),
xytext=(5, 5), textcoords='offset points', fontsize=10)
axes[1, 1].set_title('판매량 vs 재고 (크기=매출)', fontsize=14, fontweight='bold')
axes[1, 1].set_xlabel('판매량')
axes[1, 1].set_ylabel('재고')
axes[1, 1].grid(True, alpha=0.3)
plt.tight_layout()
plt.show()
예제 3: 시계열 데이터 시각화
import matplotlib.pyplot as plt
import pandas as pd
import numpy as np
# 일일 방문자 데이터 생성
dates = pd.date_range('2024-01-01', '2024-06-30', freq='D')
np.random.seed(42)
base_visitors = 1000
trend = np.linspace(0, 500, len(dates))
seasonality = 200 * np.sin(2 * np.pi * np.arange(len(dates)) / 7) # 주간 패턴
noise = np.random.normal(0, 50, len(dates))
visitors = base_visitors + trend + seasonality + noise
df = pd.DataFrame({
'date': dates,
'visitors': visitors.astype(int)
})
df['month'] = df['date'].dt.month
df['weekday'] = df['date'].dt.day_name()
# 시각화
fig = plt.figure(figsize=(16, 12))
fig.suptitle('웹사이트 방문자 분석 (2024년 상반기)', fontsize=20, fontweight='bold')
# 1. 전체 추이
ax1 = plt.subplot(3, 2, 1)
ax1.plot(df['date'], df['visitors'], linewidth=1, alpha=0.7, label='일일 방문자')
# 이동 평균
ma7 = df['visitors'].rolling(window=7).mean()
ma30 = df['visitors'].rolling(window=30).mean()
ax1.plot(df['date'], ma7, linewidth=2, label='7일 이동평균', color='orange')
ax1.plot(df['date'], ma30, linewidth=2, label='30일 이동평균', color='red')
ax1.set_title('일일 방문자 추이', fontsize=14, fontweight='bold')
ax1.set_ylabel('방문자 수')
ax1.legend()
ax1.grid(True, alpha=0.3)
# 2. 월별 평균
ax2 = plt.subplot(3, 2, 2)
monthly_avg = df.groupby('month')['visitors'].mean()
month_names = ['1월', '2월', '3월', '4월', '5월', '6월']
bars = ax2.bar(month_names, monthly_avg, color='skyblue', edgecolor='black')
ax2.set_title('월별 평균 방문자', fontsize=14, fontweight='bold')
ax2.set_ylabel('평균 방문자 수')
for bar in bars:
height = bar.get_height()
ax2.text(bar.get_x() + bar.get_width()/2., height,
f'{int(height)}', ha='center', va='bottom', fontsize=10)
ax2.grid(axis='y', alpha=0.3)
# 3. 요일별 패턴
ax3 = plt.subplot(3, 2, 3)
weekday_order = ['Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday', 'Sunday']
weekday_labels = ['월', '화', '수', '목', '금', '토', '일']
weekday_avg = df.groupby('weekday')['visitors'].mean().reindex(weekday_order)
colors = ['#FF6B6B' if day in ['Saturday', 'Sunday'] else '#4ECDC4' for day in weekday_order]
ax3.bar(weekday_labels, weekday_avg, color=colors, edgecolor='black')
ax3.set_title('요일별 평균 방문자', fontsize=14, fontweight='bold')
ax3.set_ylabel('평균 방문자 수')
ax3.grid(axis='y', alpha=0.3)
# 4. 방문자 분포
ax4 = plt.subplot(3, 2, 4)
ax4.hist(df['visitors'], bins=30, color='mediumpurple', edgecolor='black', alpha=0.7)
ax4.axvline(df['visitors'].mean(), color='red', linestyle='--',
linewidth=2, label=f"평균: {df['visitors'].mean():.0f}")
ax4.axvline(df['visitors'].median(), color='green', linestyle='--',
linewidth=2, label=f"중앙값: {df['visitors'].median():.0f}")
ax4.set_title('방문자 분포', fontsize=14, fontweight='bold')
ax4.set_xlabel('방문자 수')
ax4.set_ylabel('일수')
ax4.legend()
ax4.grid(axis='y', alpha=0.3)
# 5. 월별 박스플롯
ax5 = plt.subplot(3, 2, 5)
monthly_data = [df[df['month'] == m]['visitors'].values for m in range(1, 7)]
bp = ax5.boxplot(monthly_data, labels=month_names, patch_artist=True)
for patch in bp['boxes']:
patch.set_facecolor('lightblue')
ax5.set_title('월별 방문자 분포', fontsize=14, fontweight='bold')
ax5.set_ylabel('방문자 수')
ax5.grid(axis='y', alpha=0.3)
# 6. 통계 요약
ax6 = plt.subplot(3, 2, 6)
ax6.axis('off')
stats = f"""
📈 방문자 통계 요약
총 분석 기간: {len(df)}일
총 방문자: {df['visitors'].sum():,}명
평균 방문자: {df['visitors'].mean():.0f}명
중앙값: {df['visitors'].median():.0f}명
표준편차: {df['visitors'].std():.0f}
최대 방문: {df['visitors'].max()}명
({df[df['visitors'] == df['visitors'].max()]['date'].dt.date.values[0]})
최소 방문: {df['visitors'].min()}명
({df[df['visitors'] == df['visitors'].min()]['date'].dt.date.values[0]})
가장 많은 요일: {weekday_labels[weekday_avg.argmax()]}요일
가장 적은 요일: {weekday_labels[weekday_avg.argmin()]}요일
증가 추세: +{(df['visitors'].iloc[-30:].mean() - df['visitors'].iloc[:30].mean()):.0f}명
"""
ax6.text(0.1, 0.5, stats, fontsize=11, verticalalignment='center',
fontfamily='monospace',
bbox=dict(boxstyle='round', facecolor='lightyellow', alpha=0.5))
plt.tight_layout()
plt.show()
Guardar y Exportar
import matplotlib.pyplot as plt
# 그래프 생성
fig, ax = plt.subplots(figsize=(10, 6))
ax.plot([1, 2, 3, 4], [1, 4, 2, 3])
ax.set_title('샘플 그래프')
# 이미지로 저장
plt.savefig('graph.png', dpi=300, bbox_inches='tight') # PNG
plt.savefig('graph.pdf', bbox_inches='tight') # PDF
plt.savefig('graph.svg', bbox_inches='tight') # SVG
# 투명 배경
plt.savefig('graph.png', dpi=300, bbox_inches='tight', transparent=True)
plt.close() # 메모리 정리
Preguntas Frecuentes
한글이 깨져요!
import matplotlib.pyplot as plt
# macOS
plt.rcParams['font.family'] = 'AppleGothic'
# Windows
plt.rcParams['font.family'] = 'Malgun Gothic'
# Linux
plt.rcParams['font.family'] = 'NanumGothic'
# 마이너스 기호 깨짐 방지
plt.rcParams['axes.unicode_minus'] = False
그래프가 겹쳐요!
# tight_layout 사용
plt.tight_layout()
# 또는 여백 조정
plt.subplots_adjust(left=0.1, right=0.9, top=0.9, bottom=0.1,
wspace=0.3, hspace=0.3)
고해상도 이미지를 만들고 싶어요!
# DPI(인치당 도트 수) 높이기
fig = plt.figure(figsize=(10, 6), dpi=300)
# 또는 저장 시
plt.savefig('graph.png', dpi=300)
Pandas DataFrame을 바로 그릴 수 있나요?
import pandas as pd
df = pd.DataFrame({
'A': [1, 2, 3, 4],
'B': [4, 3, 2, 1]
})
# Pandas의 plot 메서드
df.plot(kind='line')
df.plot(kind='bar')
df.plot(kind='scatter', x='A', y='B')
plt.show()
Próximos Pasos
Matplotlib 기초를 익혔다면:
- Seaborn: 더 아름다운 통계 그래프
- Plotly: 인터랙티브 시각화
- 대시보드: Streamlit, Dash로 웹 대시보드
- 고급 시각화: 3D 그래프, 애니메이션