Computer >> 컴퓨터 >  >> 프로그래밍 >> Python

파이썬 데이터 분석 및 시각화: Pandas 핵심 가이드

Pandas는 데이터 과학과 분석 분야에서 가장 널리 사용되는 파이썬 라이브러리 중 하나입니다. 데이터 조작, 분석, 정제 작업을 손쉽게 처리할 수 있도록 도와주며, 순수 C 언어로 작성된 저수준 NumPy 위에 구축된 고수준 추상화 계층입니다. 이 글에서는 데이터 분석가나 데이터 사이언티스트라면 반드시 알아야 할 Pandas의 핵심 기능들을 실제 예제와 함께 살펴보겠습니다.

라이브러리 설치

필요한 라이브러리는 pip를 통해 간단히 설치할 수 있습니다. 명령줄 터미널에서 아래 명령어를 실행하세요.

pip install pandas

DataFrame과 Series

Pandas를 제대로 활용하려면 먼저 두 가지 핵심 데이터 구조인 DataFrameSeries를 확실히 이해해야 합니다. 이 두 구조에 대한 탄탄한 이해가 곧 Pandas 마스터의 첫걸음입니다.

Series

Series는 파이썬의 내장 자료형인 리스트(list)와 비슷하지만, 각 요소마다 인덱스(레이블)가 연결되어 있다는 점에서 차이가 있습니다.

>>> import pandas as pd
>>> my_series = pd.Series([12, 24, 36, 48, 60, 72, 84])
>>> my_series
0 12
1 24
2 36
3 48
4 60
5 72
6 84
dtype: int64

위 출력 결과에서 왼쪽이 '인덱스(index)', 오른쪽이 '값(value)'입니다. 또한 모든 Series 객체는 데이터 타입(dtype)을 가지며, 이 경우 int64입니다.

인덱스 번호를 사용해 요소를 조회할 수 있습니다.

>>> my_series[6]
84

인덱스(레이블)를 직접 지정하고 싶다면 다음과 같이 작성합니다.

>>> my_series = pd.Series([12, 24, 36, 48, 60, 72, 84], index =['ind0', 'ind1', 'ind2', 'ind3', 'ind4', 'ind5', 'ind6'])
>>> my_series
ind0 12
ind1 24
ind2 36
ind3 48
ind4 60
ind5 72
ind6 84
dtype: int64

여러 개의 요소를 인덱스로 한 번에 조회하거나 그룹 단위로 값을 할당하는 것도 매우 간단합니다.

>>> my_series[['ind0', 'ind3', 'ind6']]
ind0 12
ind3 48
ind6 84
dtype: int64
>>> my_series[['ind0', 'ind3', 'ind6']] = 36
>>> my_series
ind0 36
ind1 24
ind2 36
ind3 36
ind4 60
ind5 72
ind6 36
dtype: int64

필터링과 산술 연산 역시 쉽게 수행할 수 있습니다.

>>> my_series[my_series>24]
ind0 36
ind2 36
ind3 36
ind4 60
ind5 72
ind6 36
dtype: int64
>>> my_series[my_series < 24] * 2
Series([], dtype: int64)
>>> my_series
ind0 36
ind1 24
ind2 36
ind3 36
ind4 60
ind5 72
ind6 36
dtype: int64
>>>

그 외 Series에서 자주 사용되는 연산 몇 가지를 더 살펴보겠습니다.

>>> #딕셔너리처럼 동작합니다
>>> my_series1 = pd.Series({'a':9, 'b':18, 'c':27, 'd': 36})
>>> my_series1
a 9
b 18
c 27
d 36
dtype: int64
>>> #레이블 속성 지정
>>> my_series1.name = 'Numbers'
>>> my_series1.index.name = 'letters'
>>> my_series1
letters
a 9
b 18
c 27
d 36
Name: Numbers, dtype: int64
>>> #인덱스 변경
>>> my_series1.index = ['w', 'x', 'y', 'z']
>>> my_series1
w 9
x 18
y 27
z 36
Name: Numbers, dtype: int64
>>>

DataFrame

DataFrame은 행(row)과 열(column)로 구성된 테이블 형태의 자료구조입니다. DataFrame의 각 열은 하나의 Series 객체이며, 행은 그 Series 내부의 요소들로 이루어집니다.

DataFrame은 파이썬 내장 딕셔너리(dict)를 사용해 손쉽게 생성할 수 있습니다.

>>> df = pd.DataFrame({
    'Country': ['China', 'India', 'Indonesia', 'Pakistan'],
    'Population': [1420062022, 1368737513, 269536482, 204596442],
    'Area' : [9388211, 2973190, 1811570, 770880]
})
>>> df
  Area      Country     Population
0 9388211  China       1420062022
1 2973190  India       1368737513
2 1811570  Indonesia   269536482
3 770880   Pakistan    204596442
>>> df['Country']
0 China
1 India
2 Indonesia
3 Pakistan
Name: Country, dtype: object
>>> df.columns
Index(['Area', 'Country', 'Population'], dtype='object')
>>> df.index
RangeIndex(start=0, stop=4, step=1)
>>>

요소 접근하기

행 인덱스를 명시적으로 지정하는 방법은 여러 가지가 있습니다.

>>> df = pd.DataFrame({
    'Country': ['China', 'India', 'Indonesia', 'Pakistan'],
    'Population': [1420062022, 1368737513, 269536482, 204596442],
    'Landarea' : [9388211, 2973190, 1811570, 770880]
}, index = ['CHA', 'IND', 'IDO', 'PAK'])
>>> df
Country Landarea Population
CHA China 9388211 1420062022
IND India 2973190 1368737513
IDO Indonesia 1811570 269536482
PAK Pakistan 770880 204596442
>>> df.index = ['CHI', 'IND', 'IDO', 'PAK']
>>> df.index.name = 'Country Code'
>>> df
Country Landarea Population
Country Code
CHI China 9388211 1420062022
IND India 2973190 1368737513
IDO Indonesia 1811570 269536482
PAK Pakistan 770880 204596442
>>> df['Country']
Country Code
CHI China
IND India
IDO Indonesia
PAK Pakistan
Name: Country, dtype: object

인덱스를 이용한 행 접근은 크게 두 가지 방식으로 가능합니다.

  • .loc: 인덱스 레이블(label)을 지정하여 접근
  • .iloc: 인덱스 번호(정수 위치)를 지정하여 접근
>>> df.loc['IND']
Country             India
Landarea          2973190
Population    1368737513
Name: IND, dtype: object
>>> df.iloc[1]
Country             India
Landarea          2973190
Population    1368737513
Name: IND, dtype: object
>>>
>>> df.loc[['CHI', 'IND'], 'Population']
Country Code
CHI         1420062022
IND         1368737513
Name: Population, dtype: int64

파일 읽기와 쓰기

Pandas는 CSV, XML, HTML, Excel, SQL, JSON 등 다양한 파일 포맷을 지원합니다. 그중에서도 가장 많이 사용되는 것은 CSV 형식입니다.

CSV 파일을 읽어오려면 아래처럼 한 줄이면 충분합니다.

>>> df = pd.read_csv('GDP.csv', sep = ',')

키워드 인자 sep는 GDP.csv 파일에서 값들을 구분하는 구분 문자(separator)를 지정합니다.

집계와 그룹화(Aggregating & Grouping)

Pandas에서 데이터를 그룹화할 때는 .groupby 메서드를 사용합니다. 집계와 그룹화의 실제 활용법을 보여드리기 위해 타이타닉(Titanic) 승객 데이터셋을 사용하겠습니다. 아래 링크에서 동일한 데이터를 받을 수 있습니다.

https://yadi.sk/d/TfhJdE2k3EyALt

>>> titanic_df = pd.read_csv('titanic.csv')
>>> print(titanic_df.head())
PassengerID                                 Name  PClass 
Age \
0                    1 Allen, Miss Elisabeth Walton 1st 
29.00
1 2                     Allison, Miss Helen Loraine 1st 
2.00
2 3              Allison, Mr Hudson Joshua Creighton 1st 
30.00
3 4        Allison, Mrs Hudson JC (Bessie Waldo Daniels) 1st 
25.00
4 5                      Allison, Master Hudson Trevor 1st 0.92

     Sex        Survived        SexCode
0  female             1               1
1  female             0               1
2   male               0               0
3  female             0               1
4   male               1               0
>>>

이제 성별(남/여)에 따라 생존자와 사망자가 각각 몇 명인지 계산해 보겠습니다. .groupby를 활용하면 됩니다.

>>> print(titanic_df.groupby(['Sex', 'Survived'])['PassengerID'].count())
Sex         Survived
female       0           154
             1           308
male         0           709
             1           142
Name: PassengerID, dtype: int64

같은 데이터를 객실 등급(PClass) 기준으로 묶으면 다음과 같습니다.

>>> print(titanic_df.groupby(['PClass', 'Survived'])['PassengerID'].count())
PClass    Survived
*         0                1
1st       0              129
          1              193
2nd       0              160
          1              119
3rd       0              573
          1              138
Name: PassengerID, dtype: int64

Pandas를 활용한 시계열 분석

Pandas는 원래 시계열(time series) 데이터 분석을 위해 만들어진 라이브러리입니다. 여기서는 아마존(Amazon)의 5년치 주가 데이터를 예제로 사용하겠습니다. 아래 링크에서 다운로드할 수 있습니다.

https://finance.yahoo.com/quote/AMZN/history?period1=1397413800&period2=1555180200&interval=1mo&filter=history&frequency=1mo

>>> import pandas as pd
>>> amzn_df = pd.read_csv('AMZN.csv', index_col='Date', parse_dates=True)
>>> amzn_df = amzn_df.sort_index()
>>> print(amzn_df.info())
<class 'pandas.core.frame.DataFrame'>
DatetimeIndex: 62 entries, 2014-04-01 to 2019-04-12
Data columns (total 6 columns):
Open         62 non-null object
High         62 non-null object
Low          62 non-null object
Close        62 non-null object
Adj Close    62 non-null object
Volume       62 non-null object
dtypes: object(6)
memory usage: 1.9+ KB
None

위 코드에서는 Date 열을 DatetimeIndex로 지정해 DataFrame을 만든 뒤, 날짜순으로 정렬했습니다.

특정 월의 평균 종가(close price)는 다음과 같이 구할 수 있습니다.

>>> amzn_df.loc['2015-04', 'Close'].mean()
421.779999

데이터 시각화

Pandas 데이터는 matplotlib 라이브러리를 통해 손쉽게 시각화할 수 있습니다. 앞서 사용한 아마존 주가 데이터셋에서 특정 기간의 가격 흐름을 그래프로 확인해 보겠습니다.

>>> import matplotlib.pyplot as plt
>>> df = pd.read_csv('AMZN.csv', index_col = 'Date' , parse_dates = True)
>>> new_df = df.loc['2014-06':'2018-08', ['Close']]
>>> new_df=new_df.astype(float)
>>> new_df.plot()
<matplotlib.axes._subplots.AxesSubplot object at 0x0B9B8930>
>>> plt.show()

파이썬 데이터 분석 및 시각화: Pandas 핵심 가이드