Pandas는 데이터 과학과 분석 분야에서 가장 널리 사용되는 파이썬 라이브러리 중 하나입니다. 데이터 조작, 분석, 정제 작업을 손쉽게 처리할 수 있도록 도와주며, 순수 C 언어로 작성된 저수준 NumPy 위에 구축된 고수준 추상화 계층입니다. 이 글에서는 데이터 분석가나 데이터 사이언티스트라면 반드시 알아야 할 Pandas의 핵심 기능들을 실제 예제와 함께 살펴보겠습니다.
라이브러리 설치
필요한 라이브러리는 pip를 통해 간단히 설치할 수 있습니다. 명령줄 터미널에서 아래 명령어를 실행하세요.
pip install pandas
DataFrame과 Series
Pandas를 제대로 활용하려면 먼저 두 가지 핵심 데이터 구조인 DataFrame과 Series를 확실히 이해해야 합니다. 이 두 구조에 대한 탄탄한 이해가 곧 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()
