[Python] 데이터 사이언스 스쿨 - 5.4 Seaborn을 사용한 데이터 분포 시각화

Updated:

데이터 사이언스 스쿨 자료를 토대로 공부한 내용입니다.

실습과정에서 필요에 따라 내용의 누락 및 추가, 수정사항이 있습니다.


Seaborn을 사용한 데이터 분포 시각화

seaborn 패키지는 matplotlib 패키지를 기반으로 다양한 색상 테마와 통계 차트 등의 기능을 추가한 시각화 패키지이다.

matplotlib의 서브 패키지 pyplot에 비해 개인적으로 좀 더 예쁘게(?) 시각화 할 수 있다.

무엇보다 다양한 통계차트를 제공하는 것이 큰 장점인 것 같다.

이 챕터에선 seaborn 패키지를 이용해서 여러가지 플롯을 그려볼거다.

특별한 설명은 적지 않고 실행시켜서 잘 나오는지 위주로 확인한다.

1차원 분포 플롯

import numpy as np
import pandas as pd
import matplotlib as mpl
import matplotlib.pyplot as plt
import seaborn as sns # 별칭은 통상적으로 sns를 사용한다.

import warnings
%matplotlib inline
%config InlineBackend.figure_format = 'retina'

mpl.rc('font', family='NanumGothic') # 폰트 설정
mpl.rc('axes', unicode_minus=False) # 유니코드에서 음수 부호 설정

# 차트 스타일 설정
sns.set(font="NanumGothic", rc={"axes.unicode_minus":False}, style='darkgrid')
plt.rc("figure", figsize=(10,8))

warnings.filterwarnings("ignore")
# 붓꽃 데이터
iris = sns.load_dataset("iris")

# 타이타닉호 데이터
titanic = sns.load_dataset("titanic")

# 팁 데이터
tips = sns.load_dataset("tips")

# 여객운송 데이터
flights = sns.load_dataset("flights")

1차원 실수 플롯

# rug plot: 데이터의 위치 확인
x = iris.petal_length.values

sns.rugplot(x)
plt.title("Iris 데이터 중, 꽃잎의 길이에 대한 Rug Plot ")
plt.show()

png

# kernel density plot: 확률밀도
sns.kdeplot(x)
plt.title("Iris 데이터 중, 꽃잎의 길이에 대한 Kernel Density Plot")
plt.show()

png

# displot: 히스토그램에서 kde, rug 옵션
# distplot이 업데이트 되어 displot 혹은 histplot으로 사용
sns.displot(x, kde=True, rug=True)
plt.title("Iris 데이터 중, 꽃잎의 길이에 대한 Dist Plot")
plt.show()

png

카운트 플롯

sns.countplot(x="class", data=titanic)
plt.title("타이타닉호의 각 클래스별, 승객 수")
plt.show()

png

다차원 데이터

2차원 실수형 데이터

# jointplot: x,y scatter + hist
sns.jointplot(x="sepal_length", y="sepal_width", data=iris)
plt.suptitle("꽃받침의 길이와 넓이의 Joint Plot", y=1.02)
plt.show()

png

# jointplot: x,y scatter + kde
sns.jointplot(x="sepal_length", y="sepal_width", data=iris, kind="kde")
plt.suptitle("꽃받침의 길이와 넓이의 Joint Plot 과 Kernel Density Plot", y=1.02)
plt.show()

png

다차원 실수형 데이터

# pair plot
sns.pairplot(iris)
plt.show()

png

# hue를 이용해서 카테고리별로 분류
sns.pairplot(iris, hue="species", markers=["o", "s", "D"])
plt.suptitle("Iris Pair Plot, Hue로 꽃의 종을 시각화", y=1.03)
plt.show()

png

2차원 카테고리 데이터

titanic_size = titanic.pivot_table("survived",index="class", columns="sex", aggfunc="count")
titanic_size
sex female male
class
First 94 122
Second 76 108
Third 144 347
# heatmap
sns.heatmap(titanic_size,
            cmap = sns.light_palette("red", as_cmap=True),
            annot = True, # 빈도수 출력
            fmt = "d")

plt.title("Heatmap")
plt.show()

png

2차원 복합 데이터

# barplot
sns.barplot(x="day", y="total_bill", data=tips)
plt.title("요일 별, 전체 팁")
plt.show()

png

# boxplot
sns.boxplot(x="day", y="total_bill", data=tips)
plt.title("요일 별 전체 팁의 Box Plot")
plt.show()

png

# violinplot
sns.violinplot(x="day", y="total_bill", data=tips)
plt.title("요일 별 전체 팁의 Violin Plot")
plt.show()

png

# stripplot
# jitter=True: 데이터가 겹치지 않게 가로축상의 위치를 임의로 지정
np.random.seed(0)
sns.stripplot(x="day", y="total_bill", data=tips, jitter=True)
plt.title("요일 별 전체 팁의 Strip Plot")
plt.show()

png

# swarmplot
sns.swarmplot(x="day", y="total_bill", data=tips)
plt.title("요일 별 전체 팁의 Swarm Plot")
plt.show()

png

다차원 복합 데이터

# barplot + hue
sns.barplot(x="day", y="total_bill", hue="sex", data=tips)
plt.title("요일 별, 성별 전체 팁의 Histogram")
plt.show()

png

# boxplot + hue
sns.boxplot(x="day", y="total_bill", hue="sex", data=tips)
plt.title("요일 별, 성별 전체 팁의 Box Plot")
plt.show()

png

# violinplot + hue
sns.violinplot(x="day", y="total_bill", hue="sex", data=tips)
plt.title("요일 별, 성별 전체 팁의 Violin Plot")
plt.show()

png

# stripplot + hue
np.random.seed(0)

sns.stripplot(x="day", y="total_bill", hue="sex", data=tips, jitter=True)
plt.title("요일 별, 성별 전체 팁의 Strip Plot")
plt.legend(loc=1)
plt.show()

png

# swarmplot + hue
sns.swarmplot(x="day", y="total_bill", hue="sex", data=tips)
plt.title("요일 별, 성별 전체 팁의 Swarm Plot")
plt.legend(loc=1)
plt.show()

png

# violin + hue + split
sns.violinplot(x="day", y="total_bill", hue="sex", data=tips, split=True)
plt.title("요일 별, 성별 전체 팁의 Violin Plot, Split=True")
plt.show()

png

# stripplot + hue + dodge
sns.stripplot(x="day", y="total_bill", hue="sex",
              data=tips, jitter=True, dodge=True)
plt.title("요일 별, 성별 전체 팁의 Strip Plot, dodge=True")
plt.show()

png

# swarmplot + hue + dodge
sns.swarmplot(x="day", y="total_bill", hue="sex", data=tips, dodge=True)
plt.title("요일 별, 성별 전체 팁의 Swarm Plot, dodge=True")
plt.show()

png

# 연도, 월 별 승객 수 - 모두 하나의 값을 가지므로 pivot
flights_passengers = flights.pivot("month", "year", "passengers")

plt.title("연도, 월 별 승객수에 대한 Heatmap")
sns.heatmap(flights_passengers, annot=True, fmt="d", linewidths=1)
plt.show()

png

# survived가 notnull인 행만 데이터 프레임
data = titanic[titanic.survived.notnull()]

# catplot: hue와 row 옵션으로 3개이상 카테고리 데이터 시각화
sns.catplot(x="age", y="sex", hue="survived", row="class", data=data,
            kind="violin", split=True, height=2, aspect=4)

plt.title("각 클래스의 성별 생존자 수의 Catplot")
plt.show()

png

기타

# 그래프 겹치기
# box + strip
plt.title("Boxplot과 Strip Plot로 표현한, 요일 별 팁")

sns.boxplot(x="tip", y="day", data=tips, whis=np.inf)
sns.stripplot(x="tip", y="day", data=tips, jitter=True, color="0.4")

plt.show()

png

# 그래프 겹치기
# violin + swarm
plt.title("Violin plot과 Swarm Plot로 표현한, 요일 별 팁")

sns.violinplot(x="day", y="total_bill", data=tips, inner=None)
sns.swarmplot(x="day", y="total_bill", data=tips, color="0.9")

plt.show()

png

Seaborn 스타일

# plot 출력 함수
def sinplot(flip=1):
    x = np.linspace(0, 14, 100)
    for i in range(1, 7):
        plt.plot(x, np.sin(x + i * .5) * (7 - i) * flip)
# ticks style
sns.set_style("ticks")
sinplot()

png

# darkgrid style
sns.set_style("darkgrid")
sinplot()

png

# whitegrid
sns.set_style("whitegrid")
sinplot()

png

Leave a comment