본문 바로가기

AI가 뭐길래 왜 어려운 거죠?

EDA (ft. AI_bootcamp_개강)

글을 쓰는 현재 시점은 개강 첫주 주말이다.

돌아오는 월요일에 한주 동안 배운 내용을 시험본단다.

정말 이렇게까지 머리가 터질 것 같다는 느낌 오랜만이다.

아무래도 컴퓨터 관련 전공자가 아니기에 그런가보다.

평일에 약간의 고비가 있었지만, 인간이라면 누구나 처음 접해보는 것에 미숙하다 라는 생각으로 

조급해하지 않고 자신에게 실망하지 않고, 내가 할 수 있는 만큼의 최선을 다해 하루를 보내보자

라는 긍정 마인드를 다시 되새긴다. 

아직 할일이 산더미인데 벌써 일요일 저녁 아홉시이다. 

안녕 나의 주말,,

 

 


Section1_Sprint1_Note1&Note2
  • 학습목표
    • EDA에 대해서 이해한다.
    • Feature Engineering의 목적을 이해할 수 있다.
    • Business Insight를 도출할 수 있다. 

통계 및 시각화를 통해 데이터를 탐색하고 이해한 후, 데이터를 분석 및 정제하여 유의미한 결과를 도출해낸다.
  • EDA
    • 통계시각화를 통해 
    • 데이터를 탐색이해하는 과정
  • Feature Engineering
    • 도메인 지식과 수학적 연산을 통해
    • Raw Data로 부터 유용한 featrue를 도출해내는 과정
    • GIGO(raw data 자체로 머신러닝 모델을 작동시킬 수 없다)
    • 세세한 분석과 모델의 성능을 높이기 위해 필요한 과정 
  • Business Insight
    • EDA작업을 하는 이유 : Business Insight를 도출하기 위함
    • 도출하기 위해서는 도메인 지식이 반드시 필요하다
    • ** 도메인 지식: 분석하고자 하는 분야의 정보

< 목차 >

1. 불러오기

  • pd.read_csv()
  • pd.read_excel()

2. 탐색

  • .shape
  • .info()
  • .describe()
  • .head()
  • .duplicated()
  • .drop_duplicates()
  • .reset_index(drop=True)

3. Feautre Engineering

  • np.repeat()
  • .rename(, inplace=True)
  • .columns
  • set()
  • .append()
  • .to_csv

4. 통계 및 시각화

  • .groupby( , as_index=False)
  • .mean()
  • .value_counts()
  • .counts()
  • .query()
  • .median()
  • .format()
  • .plot(kind='bar')
  • matplotlib.pyplot

Part 0. Introduction

  • 기획 배경
    • 데이터 분석의 목적은 궁금한 질문에 대한 답을 도출하기 위함이다.
    • 즉, 데이터 탐색 및 이해과정을 거친 분석 작업을 통해 도출된 유의미한 결과로 질문에 대하여 대답한다.
 e.g. 와인 데이터로 "높은 퀄리티의 와인은 어떤 화학적 특징(성분)을 가지고 있을까"에 대한 답을 도출한다.

 

  • Data Description
    • 데이터 Description을 통해 Independent Variables와 Dependent Variables 사이의 관계를 알아본다.
    • 이후, 어떤 Business Question을 도출할 수 있을 지 생각해본다.
e.g. 와인 데이터를 통해 다양한 와인의 성분과 등급 사이의 관계를 알아본다.
       와인 데이터 descroption을 살펴보고, 데이터를 통해 어떤 질문을 도출할 수 있을지 생각해본다.
       와인 성분 (independent variables; cause), 와인 등급/퀄리티 (dependent variables; efffect)

Part 1.Gathering Data

데이터 불러오기 -  .read_csv() 메서드 활용

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import seaborn as sns

 

# 데이터 업로드
from google.colab import files
uploaded = files.upload()
from google.colab import drive
drive.mount('/content/drive')

 

# .read_csv() 활용하여 데이터 불러오기 
df = pd.read_csv('파일명.csv')
df = pd.read_excel('파일명.xlsx')
# csv; comma sperated value : 콤마(,)로 구분되어 있는 파일을 의미함
# 만약 콤마가 아닌 다른 값으로 구분되어 있는 데이터는?
df = pd.read_csv('파일명.csv', sep=';')
# 세미콜론(;)으로 구분된 데이터를 불러온다
# 불러오고 .head() 메서드로 dataframe형태로 잘 불러와졌는지 확인한다

[.read_csv() 공식 문서]

https://pandas.pydata.org/docs/reference/api/pandas.read_csv.html


Part 2. EDA

pandas 메서드로 보는 간단한 탐색

  • 각 데이터셋의 shape 및 column 개수 확인
  • 결측치(missing values) 및 중복(duplicated) 데이터 여부
  • 타겟인 quality column의 유니크한 값의 개수 확인

1) .shape

  • 하나의 Row에는 하나의 데이터(관측치)
  • 하나의 Column에는 하나의 변수
print(df.shape)	# 데이터의 Row와 Column의 개수 확인 
df.shape	# (Rows, Columns)의 형태로 출력

 

2) .info()

df.info()	# Rows와 Columns의 크기, Columns 이름, Data type 등 확인
e.g.
out [  ] :
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 350 entries, 0 to 349
Data columns (total 6 columns):
# Column Non-Null Count Dtype
--- -------- ----------------------- -----
0 이름      350 non-null       object
1 경구용인슐린 350 non-null object
2 주사제인슐린 350 non-null object
3 혈당수치시작 350 non-null float64
4 혈당수치끝 350 non-null float64
5 혈당수치변화 213 non-null float64
dtypes: float64(3), object(3)
memory usage: 16.5+ KB

 

3) .describe()

df.describe()	
# numerical data types(수치적 데이터 타입)의 descriptive states(평균, 표준표차, 최소/최대값 등) 확인
e.g.
Out [  ] : 

  혈당수치_시작 혈당수치_끝
count 350.000000 350.000000
mean 7.956343 7.560057
std 0.540657 0.545328
min 7.500000 7.010000
25% 7.650000 7.270000
50% 7.785000 7.400000
75% 7.950000 7.557500
max 9.950000 9.580000

 

4) .duplicated()

# 중복된 데이터 개수 확인
df.duplicated().sum()
# drop_duplciates()를 통해 중복된 데이터 제거
df = df.drop_duplicates()
# 제거된 후, 결과물 확인
df.head()
# 중복데이터 제거 후, index 재정렬
df = df.reset_index(drop=True)
# drop=True : index값을 새로운 column으로 넣지 않는다

[.reset_index() 공식 문서]

https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.reset_index.html


Feature Engineering

  • GIGO; Garbage In, Garbage Out
  • Raw Data는 매우 지저분한 상태이므로 머신러닝 모델에 제대로 작동하지 않는다.
  • 세세한 분석과 모델의 성능을 높이기 위해, feature를 재조합하여 의미있는 데이터를 추가할 수 있다.
  • 즉, 도메인 지식과 창의성/수학적 연산을 바탕으로 기존 feature들을 재조합하여 새로운/유의미한 feature를 도출해내는 과정이다.

Price_per_Weight를 만들어내는 과정이 Feature Engineering이다.

 

1)  .repeat()

  • 데이터 분석을 효율적으로 하기 위해, 2개로 분리된 DataSet을 합친다.
e.g. 화이트와인과 레드와인 데이터셋을 합치기 위해, 와인의 종류(레드/화이트)가 담긴 새 컬럼을 추가해야한다.
       이를 .repeat() 메서드를 활용해 Feature Engineering을 시행해본다.
# red dataframe에 red를 나타내는 array 생성
red_color = np.repeat('red', len(df_red))
red_color
# 위에서 만든 array를 dataframe 추가
df_red['color'] = red_color
# 새 컬럼, 'color'가 red 데이터셋에 추가되었는지 확인
df_red.columns
# 2개의 데이터를 합치기 위해, 합치려는 데이터셋의 columns가 동일한지 확인해야 한다
set(df_red.columns) == set(df_white.columns)
# 동일하지 않은 column의 이름 수정
df_red.rename(columns = {'total_sulfur-dioxide' : 'total_sulfur_dioxide'}, inplace=True)
# 수정 후, 결과물 확인
df_red.columns
df_white.columns
set(df_red.columns) == set(df_white.columns)

 

2) .append()

# 하나의 데이터셋으로 통합
df = df_white.append(df_red, ignore_index=True)
# 두개의 DataFrames 잘 합쳐졌는지 결과물 확인
df.shape
df.head()
# 합쳐진 DataFrame은 분석하고자 하는 final version이므로 csv파일로 저장
df.to_csv('winequality_edited.csv', index=False)
## .to_csv() 메서드 활용할 때, index=False 파라미터를 지정하게 되면 첫번째 컬럼이 인덱스로 지정됨 
## 이를 꼭 지정하여 export 해줘야함

[.append() 공식 문서]

https://pandas.pydata.org/pandas-docs/stable/reference/api/pandas.DataFrame.append.html


통계값 및 시각화 활용

  • Independent Variables와 Dependent Variables 간의 관계를 알아보며 Business Question에 대한 답을 살펴본다.
  • 이러한 관계를 통계기법(평균, 분산, 표준편차 등)과 시각화를 통해 다방면의 데이터 분석을 할 수 있다 .
e.g.
Business question: 높은 퀄리티의 와인은 어떤 화학적 특징을 가지고 있는가?
와인의 특징/성분(independent variables)와 퀄리티(dependent variables)간의 관계를 알아본다
# 저장했던 통합 데이터셋 업로드
wine_df = pd.read_csv('winequality_edited.csv')
winde_df.head()

 

1) .groupby()

  • 데이터 집계(aggregation)에서 유용하게 사용한다.
  • 데이터를 그룹으로 묶어, 그룹별 통계연산과 집계, 요약을 빠르게 할 수 있다. 

wine_df.grouby('quality').mean() : 와인 등급별 feature들의 평균

# 어떤 종류의 와인이 더 높은 평균(quality rating)을 받을까?
# mean function으로 각 컬럼의 평균값을 구할 수 있음
wine_df.mean()
# 위의 코드는 와인의 color에 따른 평균 quality를 비교할 수 없다
# 따라서 groupby()를 활용해야한다
wine_df.groupby('color').mean()

wine_df.groupby('color').mean()의 결과값

# 위의 많은 컬럼 중, quality 컬럼 하나만을 선택하여 확인
wine_df.groupby('color)['quality).mean()

wine_df.groupby('color')['quality'].mean()의 결과값

# 위와 같이 groupby 안에 지정하는 컬럼들은 DataFrame의 인덱스로 지정됨
# 이를 원하지 않으면, 'as_index=False' 파라미터를 지정
wine_df.groupby('color', as_index=False)['quality'].mean()

wine_df.groupby('color', as_index=False)['quality'].mean()의 결과값

wine_df['color'].vaule_counts()
🔎 해설
ㅇ color에 따른 quality를 통계적으로 확인해보니, white와인이 근소하게 높은 평균 quality를 가짐을 확인할 수 있다.
ㅇ 이 원인이 단순하게 white 와인 데이터가 많기 때문인지 아니면 
ㅇ 실제로 white 와인의 quality가 평균적으로 높은지에 대해서는 추가적인 분석이 필요해 보인다.

 

 color에 따른 평균 pH지수를, 와인의 quality에 따라 살펴본다. 

# 와인의 quality에 따른 각 컬럼의 평균값 확인
wine_df.grouby('quality').mean()
# groupby는 하나 이상의 컬럼으로 묶을 수 있음
# quality, color로 그룹지어 각 컬럼의 평균값 확인
wine_df.grouby(['quality', 'color']).mean()

wine_df.groupby(['quality', 'color']).mean()의 결과값

wine_df.groupby(['quality', 'color'], as_index=False).mean()
# as_index=False 파라미터를 사용하면, 그룹으로 묶었던 컬럼들이 
# index가 아닌 coloumn으로 지정되는 것을 볼 수 있다

wine_df.groupby(['quality', 'color']), as_index=False.mean()의 결과값

# 위의 많은 컬럼 중, 알아내고자 하는 pH 컬럼을 선택하여 확인
wine_df.groupby(['quality', 'color'], as_index=False)['pH'].mean()

wine_df.groupby(['quality', 'color'], as_index=False)['pH'].mean()의 결과값

🔎 해설
위의 통계치를 통해, 같은 퀄리티라 하더라도, 화이트 와인이 레드에 비해 pH지수가 더 낮음을 확인할 수 있다.
그렇다면 color의 구분없이, 어떤 pH지수 등급을 가진 와인이 더 높은 평균 quality rating을 받을까?
와인의 pH등급은 4단계로 구분할 수 있다. 
ㅇ Low: Lowest 25% pH values
ㅇ Medium: 25% - 50% of pH values
ㅇ Moderately High: 50% - 75% of pH values
ㅇ High: max pH values
wine_df.pH.describe()
# pH는 continuous data이지만, 
# pH 등급에 따라 quality rating이 어떻게 달라지는 알아보기 위해
# continuous data를 category로 바꾸어야 한다. 
# pandas의 cut function을 이용해본다.
# cut의 bins 파라미터는, .describe()을 이용하여 확인한 4분위수를 활용할 수 있다.
# wine_df.pH.describe() 를 통해 확인한 4분위수를 활용하여 bins로 입력
bins = [2.72, 3.11, 3.21, 3.33, 4.01]
# 범위에 따라 원하는 레이블명을 입력
labels = ['Low', 'Medium', 'Moderately High', 'High']
# cut을 통해 continuous data를 category data로 변경
wine_df['ph_levels'] = pd.cut(x=wine_df['pH'], bins=bins, labels=labels)
# 결과 확인
wine_df.head()

cut fucntion실행 후, wine_df.describe()의 결과값

# ph_levles에 따른 평균 quality 확인
wine_df.groupby('ph_levels', as_index=False)['quality'].mean()

wine_df.groupby('ph_levels', as_index=False)['quality'].mean()의 결과값

 

신맛 말고, 단맛(residual_sugar)과 떫은 맛(chlorides)은 어떤 성분에 영향을 받을까?

# 색상에 따른 평균 residual_sugar 확인
wine_df.groupby('color', as_index=False)['residual_sugar'].mean()
# 화인트 와인이 월등히 높음

색상에 따른 평균 residual_sugar 확인 결과값

# 퀄리티와 색상에 따른 평균 residual_sugar 확인
group_residual_sugar = wine_df.groupby(['quality', 'color'], as_index=False)['residual_sugar'].mean()

퀄리티와 컬러에 따른 평균 잔류설탕확인 결과값

group_residaul_sugar.plot(kind='bar')	
# 퀄리티와 컬러에 따른 평균 잔류설탕 확인을 시각화로 확인

퀄리티와 컬러에 따른 평균 잔류설탕을 시각화로 확인

 

🔎 해설
시각화 자료를 통해 레드에 비해 화이트 와인의 잔류설탕(residual_sugar)가 월등히 높은 것을 확인할 수 있다. 
특히 시각화 결과를 보면, 모든 컬리티에서 화이트와인이 레드에 비해 더 덜다고 확인된다. 

 

그렇다면 떫은 맛은(chlorides)은 어떻게 볼까? chlorides 성분이 많을수록 떫은 맛이 강하다.

# 색상에 따른 평균 chlorides(염화나트륨) 확인
wine_df.groupby('color')['cholrides'].mean()

색상에 따른 평균 chlorides 확인 결과값

🔎 해설
수치 확인 결과, 화이트에 비해 레드가 더 높은 것을 확인할 수 있다. 

 

와인의 향(aroma)도 중요한 역할을 담당하기에 volatile_acidity(휘발성산, 아세트산)성분을 확인해본다.

# quality에 따른 휘발성산의 차이를 scatter plot으로 확인
import matplotlib.pyplot as plt
plt.scatter(wine_df['quality'], wine_df['votaile_acidity']);

퀄리티에 따른 휘발성산의 차이를 scatter plot으로 확인한 결과값

# quality에 따른 평균 volatile_acidity 확인
group_volatile_acidity = wine_df['volatile_acidity'].groupby(wine_df.['quality'])
# group_volatile_acidity = wine_df.groupby('quality)['volatile_quality']와 같은 결과값 도출
print(group_volatile_acidity.mean())	# 평균 출력
# 평균값을 matplotlib의 plot으로 시각화 확인
plt.plot(group_volatile_acidity.mean()); # 세미콜론(;)을 꼭 붙인다.

print(wine_df['volatile_acidity'].groupby(wine_df['quality']).mean())의 결과값 / 수치의 시각화 결과값

 

🔎 해설
- 퀄리티에 따른 휘발성산의 차이를 두 가지 시각화 방법으로 확인해보았다.
  ㅇ scatter plot 시각화 결과는, 한 눈에 해석하기 어렵다.
  ㅇ 반면, line plot으로 확인한 결과는, 상대적으로 변화가 눈에 잘 들어오는 것을 알 수 있다.
- 시각화 결과, 상대적으로 퀄리티 등급이 높은 와인이 평균 휘발성산 수치가 낮은 것을 알 수 있었다.
  ㅇ 즉, 휘발성산 수치가 높은 와인은 코를 찌르는 듯한 날카로운 냄새가 나기때문에
  ㅇ 휘발성산 수치가 낲은 와인이 본연의 포도향을 더 잘 드러낸다는 것을 알 수 있다.   

 

와인의 바디감도 품질 결정에 중요한 역할을 하므로 바디감도 확인해봐야한다. 

# quality에 따른 평균 밀도 확인
group_density = wine_df['density'].groupby(wine_df['quality'])
print(group_density.mean())
# plot으로 시각화
plt.plot(group_density.mean())

quality에 따른 평균 density 수치 확인 결과값 / 평균 밀도 수치를 시각화 확인한 결과값

🔎 해설
ㅇ 퀄리티가 높아질수록 밀도 수치는 낮아지므로 좋은 와인일수록 물의 밀도가 낮은 와인임을 확인할 수 있다. 

[.groupby() 공식 문서]

https://pandas.pydata.org/pandas-docs/stable/user_guide/groupby.html

 

2) .query()

  • DataFrame에서 원하는 rows를 선택하기 위한 두 가지 방법이 존재한다.
    • index 사용
    • .query() 함수 사용
# cancer data에서 malignant rows만 선택한다
maglinant_cancer = df[df['diagnosis'] == 'Malignant']
maglinan_cancer = df.query('diagnosis == "Malignant"')

.query() 함수를 활용해, 와인의 바디감을 결정하는 데에 중요한 alcohol을 살펴본다.

- alcohol 도수가 높을수록 바디감이 높아진다. 도수가 높은 와인이 더 높은 퀄리티 등급을 받는지 알아본다. 
- alcohol에 따라 구분되는 3개의 바디감 그룹으로 데이터를 나눈다. 
  ㅇ Light alcohol        : 12.5% 이하
  ㅇ Medium alcohol   : 12.5% ~ 13.5%
  ㅇ Full alcohol          : 13.5% 이상
# .query() 함수를 이용해 데이터 구분
light_body = wine_df.query("alcohol <= 12.5")
medium_body = wine_df.query("(alcohol > 12.5) and (alcohol <13.5)")
full_body = wine_df.query("alcohol >= 13.5")
# 두 개의 DataFrame이 missing rows 없이 잘 나누어졌는지 확인
print(wine_df.shape)
print(light_body.shape, medium_body.shape, full_body.shape)

# 직접 더해 확인할 수도 있지만, 아래의 코드를 이용해 편리하게 확인 가능
num_samples = wine_df.shape[0]
print(num_samples)
print(light_body.count())
num_samples == light_body.count() + medium_body.count() + full_body.count()

print(num_samples) 결과값 / print(light_body.count()) 결과값 / num_samples == 합계(light/medium/full_body.count) 결과값

# 낮은 알콜 함량 와인의 평균 quality 확인
light_body.quality.mean()
# 높은 알콜 함량 와인의 평균 quality 확인
full_body.quality.mean()

낮은/높은 알콜 함량 와인 평균 quality 확인 결과값

print('Mean quality value for wine with {} alcohol content : {:.2f}'.format("low", light_body.quality.mean()))
print('Mean quality value for wine with {} alcohol content : {:.2f}'.format("medium", medium_body.quality.mean()))
print('Mean quality value for wine with {} alcohol content : {:.2f}'.format("high", full_body.quality.mean()))

낮은/중간/높은 알콜 함량 와인의 평균 quality 확인 결과값

🔎 해설
- alcohol 도수가 높을 수록 바디감이 무거워진다. 
  ㅇ 상대적으로 높은 퀄리티의 와인의 바디감이 무겁다는 것을 알 수 있다.
  ㅇ 하지만 무조건 바디감이 높아야 와인의 퀄리티가 높은 것은 아니라는 것을 확인할 수 있다.
  ㅇ 와인의 여러 특징들이 조화로울 때, 좋은 품질의 와인이라고 할 수 있다.

residual_sugar(단맛/잔류설탕)에 대한 정보를 .groupby()가 아닌 .query()를 활용해 살펴본다. 

ㅇ residual_sugar 함량이 높은 와인이 더 높은 quality를 받늕 알아보기 위해,
ㅇ DataSet을 median 값 기준으로 나누어 각 그룹의 평균 quality rating을 확인해본다. 
# residual_sugar 함량의 median 값 확인
sugar_med = wine_df.residual_sugar.median()
print(sugar_med)
# query() 함수를 이용해 median 값 기준으로 두 개의 데이터 프레임 생성
low_sugar = wine_df.query("residual_sugar < @sugar_med")
high_sugar = wine_df.query("residual_sugar >= @sugar_med")
# 동일한 DataSet 개수인지 확인
num_samples = wine_df.shape[0] 
num_samples == low_sugar.quality.count() + high_sugar.quality.count()

sugar_med 결과값 / num_samples == 합계(low/high_sugar.quality.count())

# 낮은 residual_sugar 함량 와인의 평균 quality 확인
print(low_sugar.quality.mean())
# 높은 residual_sugar 함량 와인의 평균 quality 확인
high_sugar.quality.mean()

low_sugar / high_sugar 와인의 평균 quality 확인 결과값


Part 3. Business Insight

ㅇ 지금까지 다양한 EDA 방법을 통해, 와인 quality에 영향을 미치는 성분들을 확인해보았다. 
ㅇ 이렇게 EDA 를 진행한 이유는 무엇인가?
ㅇ Data를 통해 분석한 내용을 바탕으로, Business Insight를 도출하기 위함이다. 
ㅇ 높은 퀄리티의 와인이 가지는 특징을 알아낸다면, 이를 비즈니스적으로 활용할 수 있다.  
와인 성분에서 중요한 부분을, 크게 4가지로 구분하여 분석을 정리해본다. 
1. pH
  ㅇ pH를 4개의 등급으로 나누어 각 등급에 따른 평균 quality rating 을 확인했다. 
  ㅇ pH지수가 높다면 비교적 quality 역시 높게 나왔지만, 반드시 그런 것만은 아니었다. 
2. 맛
  ㅇ residual_sugar : 레드에 비해 화이트 와인의 당도가 더 높게 기록되었다.
  ㅇ chlorides : 높은 quality 등급일수록 chlorides 수치가 낮은(떫은맛이 덜하다는) 것을 알 수 있었다.  
3. volatile_acidity(아로마)
  ㅇ 높은 quality의 와인일수록 비교적 낮은 volatile_acidity 수치를 확인했다.
4. alcohol(바디감)
  ㅇ 높은 quality의 와인일수록 와인의 바디감이 무겁다는(알콜 도수가 높다는) 것을 확인했다. 
< pH & alcohol 지수가 높고 chlorides & volatile_acidity는 낮은 성분의 와인이 비교적 좋은 quality의 와인이다라는 것을 알 수 있었다. >

ㅇ 이러한 Business Insight를 도출하기 위해서는 도메인 지식이 반드시 필요하다.
       ** 도메인 지식: 분석하고자 하는 분야의 정보
ㅇ 도메인 지식없이 데이터를 본다면, Data는 단순한 문자 혹은 숫자의 결합에 불과하다. 

Part 4. Conclusion

마지막으로 개선된 시각화를 통해, 와인의 quality와 다양한 특성들 사이의 관계를 확인해본다.

Visiualization 1

와인의 종류가 레드 또는 화이트인지에 따라 더 높은 quality를 가지는지 시각화를 통해 확인한다.
# 와인의 컬리에 따라 더 높은 퀄리티를 가지는지 시각화 확인
wine_df.groupby('color')['quality'].mean().plot(kind='bar',
                                              title='Average Wine Quality by Color',
                                              fontsize=13,
                                              color=['red', 'blue'],
                                              alpha=0.4)
# alpha : graph의 투명도 설정할 수 있다.
# default 값 : alpha=1 - / 숫자가 작아질수록 투명해짐

🔎 해설
ㅇ 화이트 와인이 레드보다 아주 근소하게 높은 평균 quality rating을 보여준다.
counts = wine_df.groupby(['quality', 'color']).count()['pH']
counts.plot(kind='bar',
            color=['red', 'blue'],
            title='Counts by Wine Quality and Color', 
            fontsize=15,
            alpha=0.4)

🔎 해설
ㅇ 화이트 와인이 quality rating 5,6,7에서 더 많은 개수를 가지고 있음을 알 수 있다.
ㅇ 따라서 화이트 와인의 평균 quality rating이 다소 높은 이유를 확인할 수 있다.
ㅇ pandas에 내장되어 있는 시각화 방법은 시각적으로 이상적이지 않기 때문에,
ㅇ 주로 분석가 스스로 간단하게 보기 위함이고,
전문적인 시각화 자료를 도출하기 위해서는 matplotlib이나 seaborn library를 이용하는 것이 좋다  

[.query() 공식 문서]

https://pandas.pydata.org/pandas-docs/stable/user_guide/groupby.html

 

2023.02.19(일)