insert
메서드는 DataFrame의 특정 위치에 열을 삽입하는 메서드입니다..
DataFrame에 해당 열이 이미 존재 할 경우 allow_duplicates=True
가 아니면 Value Errer를 발생시킵니다.
df.insert(loc, column, value, allow_duplicates=False)
loc
: 삽입될 열의 위치
column
: 삽입될 열의 이름
val
: 삽입될 열의 값
allow_duplicates
: {True or False} 기본값은 False로 True일경우 중복 열의 삽입을 허용합니다.
data = [[1,2,3],[4,5,6],[7,8,9]]
col = ['col1','col2','col3']
row = ['row1','row2','row3']
df = pd.DataFrame(data=data,index=row,columns=col)
print(df)
>>
col1 col2 col3
row1 1 2 3
row2 4 5 6
row3 7 8 9
loc
=3으로해서 4열로 설정, column
을 통해 이름을 col4
로하고 value
로 값을 설정하여 열을 추가해보겠습니다.
df.insert(3,'col4',[10,11,12])#col4라는 열을 10,11,12로 삽입한다
print(df)
>>
col1 col2 col3 col4
row1 1 2 3 10
row2 4 5 6 11
row3 7 8 9 12
col4가 3번열에 추가된 것을 확인할 수 있습니다. (0번부터 시작하기 때문에 3번 열은 4번째 열입니다.)
그럼 이미 추가되어있는 'col3'을 추가하면 어떻게 될까요? 바로 오류를 발생시키게 됩니다.
df.insert(3,'col3',[10,11,12],allow_duplicates=False)
print(df)
>>
ValueError: cannot insert col3, already exists
여기서 allow_duplicates=True하면 중복된 이름으로 col3이 추가되는것을 확인 할 수 있습니다.
df.insert(3,'col3',[10,11,12],allow_duplicates=True)
print(df)
>>
col1 col2 col3 col3
row1 1 2 3 10
row2 4 5 6 11
row3 7 8 9 12
pop
메서드는 DataFrame에서 열 레이블을 꺼냅니다. 즉, 원본 DataFrame에서 해당 열이 제거됩니다.
df.pop(item)
item
: 꺼낼 열의 이름입니다.
data = [[1,2,3,4],[5,6,7,8],[9,10,11,12],[13,14,15,16]]
col = ['col1','col2','col3','col4']
row = ['row1','row2','row3','row4']
df = pd.DataFrame(data=data,index=row,columns=col)
print(df)
col1 col2 col3 col4
row1 1 2 3 4
row2 5 6 7 8
row3 9 10 11 12
row4 13 14 15 16
item에 col3을 입력하여 열을 꺼내보겠숩나다.
pop
한 것을 변수에 넣어 출력해 보면 해당 열이 출력 되는것을 확인 할 수 있습니다.
item = df.pop('col3')
print(item)
row1 3
row2 7
row3 11
row4 15
Name: col3, dtype: int64
원본이었던 df는 어떻게 되었을까요? pop함수는 원본에서 꺼낸다는 의미이기 때문에, col3
이 원본에서 삭제된것을 알 수 있습니다.
print(df)
>>
col1 col2 col4
row1 1 2 4
row2 5 6 8
row3 9 10 12
row4 13 14 16
Pandas객체를 복사합니다. deep copy와 shallow copy기능을 지원합니다.
deep
: {True or False} 기본값 True
deep
= True
인 경우를 deep copy라고 하며 원본과는 완전하게 별개인 복사본이 생성됩니다. 사본과 원본의 수정은 서로에게 영향을 끼치지 않습니다.
deep
= False
인 경우를 shallow copy라고 하며 원본의 데이터 및 인덱스를 복사하지않고 새 객체를 호출합니다.
즉, 원본의 데이터가 수정되면 사본의 데이터도 수정되며, 그 반대도 마찬가지 입니다.
먼저, 아래와 같이 series객체를 하나 만들고, deep copy본과 shallow copy본인 객체를 생성해봅니다.
sr = pd.Series([1, 2], index=["col1", "col2"])
deep = sr.copy(deep=True)
shallow = sr.copy(deep=False)
print(sr)
col1 1
col2 2
dtype: int64
이제 원본인 sr과 deep copy본인 deep, shallow copy본인 shallow의 요소를 변경하고 다시 출력해보겠습니다.
sr[0] = 9
shallow[1] = 8
deep[1]=7
원본 출력시
shallow에서 변경한 내용이 원본인 sr에도 적용된 것을 확인할 수 있습니다.
Copyprint(sr)
>>
col1 9
col2 8
dtype: int64
shallow copy본 출력시
sr에서 변경한 내용이 사본인 shallow에도 적용된 것을 확인할 수 있습니다.
print(shallow)
col1 9
col2 8
dtype: int64
deep copy본 출력시
원본이나 다른 사본의 변경내용과 무관하게 자기 자신의 변경내용만이 적용된 것을 확인할 수 있습니다.
print(deep)
col1 1
col2 7
dtype: int64
마찬가지로 기본적인 3x3 DataFrame객체를 생성해보겠습니다.
col = ['col1','col2','col3']
row = ['row1','row2','row3']
df = pd.DataFrame(data=[[1,2,3],[4,5,6],[7,8,9]],index=row,columns=col)
deep = df.copy(deep=True)
shallow = df.copy(deep=False)
print(df)
>>
col1 col2 col3
row1 1 2 3
row2 4 5 6
row3 7 8 9
이제 원본과 copy본의 값을 아래와 같이 변경하고 출력해보겠습니다.
df['col1']['row1']=99
shallow['col2']['row2']=88
deep['col2']['row2']=77
원본 출력시
print(df)
#shallow에서 변경한 내용이 원본인 df에도 적용된 것을 확인할 수 있습니다.
col1 col2 col3
row1 99 2 3
row2 4 88 6
row3 7 8 9
shallow copy본 출력시
print(shallow)
#df에서 변경한 내용이 사본인 shallow에도 적용된 것을 확인할 수 있습니다.
col1 col2 col3
row1 99 2 3
row2 4 88 6
row3 7 8 9
deep copy본 출력시
Copyprint(deep)
#원본이나 다른 사본의 변경내용과 무관하게 자기 자신의 변경내용만이 적용된 것을 확인할 수 있습니다.
col1 col2 col3
row1 1 2 3
row2 4 77 6
row3 7 8 9
drop
메서드는 데이터프레임에서 열을 삭제하는 메서드입니다.
pop
메서드와는 다르게 원본이 변경되지 않습니다.
labels
: 삭제할 레이블명입니다. axis
를 지정해주어야합니다.
axis
: {0 : index / 1 : columns} labels
인수를 사용할경우 지정할 축입니다.
index
: 인덱스명을 입력해서 바로 삭제를 할 수 있습니다.
columns
: 컬럼명을 입력해서 바로 삭제를 할 수 있습니다.
level
: 멀티인덱스의 경우 레벨을 지정해서 진행할 수 있습니다.
inplace
: 원본을 변경할지 여부입니다. True
일경우 원본이 변경됩니다.
errors
: 삭제할 레이블을 찾지 못할경우 오류를 띄울지 여부입니다. ignore
할 경우 존재하는 레이블만 삭제됩니다.
※ axis=0
+ labels
는 index
인수와 역할이 같고 axis=1
+ labels
는 columns
와 역할이 같습니다.
sr = pd.Series([1, 2], index=["col1", "col2"])
deep = sr.copy(deep=True)
shallow = sr.copy(deep=False
print(sr)
>>
col1 1
col2 2
dtype: int64
이제 원본인 sr과 deep copy본인 deep, shallow copy본인 shallow의 요소를 변경하고 다시 출력해보겠습니다.
row = ['row1','row2','row3']
col = ['col1','col2','col3']
data = [[1,2,3],[4,5,6],[7,8,9]]
df = pd.DataFrame(data=data, index=row, columns=col)
print(df)
col1 col2 col3
row1 1 2 3
row2 4 5 6
row3 7 8 9
labels인수와 axis인수로 삭제
labels
인수로 삭제할 레이블명을 지정해주게되면, axis
인수를 통해 해당 레이블(축)을 지정해주어야합니다.
row2
를 삭제해보겠습니다.
print(df.drop(labels='row2',axis=0))
col1 col2 col3
row1 1 2 3
row3 7 8 9
col2
를 삭제해보겠습니다.
print(df.drop(labels='col2',axis=1))
col1 col3
row1 1 3
row2 4 6
row3 7 9
index인수와 columns 인수로 삭제
index
인수와 columns
인수를 사용하면 labels
인수와 axis
사용 없이 삭제가 가능합니다.
index
를 사용해서 row3
을 삭제해보겠습니다.
print(df.drop(index='row3'))
col1 col2 col3
row1 1 2 3
row2 4 5 6
columns
를 이용해 col3
을 삭제해보겠습니다.
print(df.drop(columns='col3'))
col1 col2
row1 1 2
row2 4 5
row3 7 8
errors인수 예시
삭제하고자하는 레이블이 존재하지 않으면 오류가 발생하게됩니다. errors='ignore'
로 설정하면 오류를 발생하지 않습니다.
row3
, row4
를 삭제해보겠습니다.(row4
는 존재하지 않음)
print(df.drop(labels=['row3','row4'],errors='raise'))
KeyError: "['row4'] not found in axis"
row4
가 존재하지 않기 때문에 오류가 발생하였습니다. errors='ignore'
로 실행해보겠습니다.
print(df.drop(labels=['row3','row4'],errors='ignore'))
col1 col2 col3
row1 1 2 3
row2 4 5 6
오류없이 존재하는 row3
이 삭제된 것을 확인할 수 있습니다.
inplace인수로 원본 변경
inplace
인수는 Pandas객체의 공통사항으로 원본의 변경여부를 의미합니다.
True
일 경우 반환값 없이 원본이 변경됩니다.
df.drop(labels=['col1','col2'],axis=1,inplace=True)
print(df)
col3
row1 3
row2 6
row3 9
append
메서드는 데이터프레임에 행을 추가하는 메서드입니다.
두 데이터프레임 객체를 행 기준으로 합치는 개념입니다.
기본 사용
other
: self
객체에 행 기준으로 합칠 객체입니다.
ignore_index
: 기존 인덱스를 사용할지 여부 입니다. False
로 할 경우 0,1,2,..,n 이 부여됩니다.
verify_integrity
: 합칠 때 이름이 중복되는 인덱스가 있을 경우 오류를 발생시킬지 여부 입니다.
sort
: 열을 사전적으로 정렬할 지 여부입니다.
df = pd.DataFrame(data=[[1,2],[3,4]], index=['row1','row2'], columns=['col1','col3'])
print(df)
>>
col1 col3
row1 1 2
row2 3 4
기본적인 사용법(+sort, ignore_index)
먼저 간단한 df2
를 만들어 pd.concat로 df
와 합쳐보겠습니다.
df2 = pd.DataFrame(data=[[5,6]],index=['row3'],columns=['col2','col4'])
print(df2)
>>
col2 col4
row3 5 6
print(pd.concat([df,df2]))#리스트 형태로 해줘야 한다
>>
col1 col3 col2 col4
row1 1.0 2.0 NaN NaN
row2 3.0 4.0 NaN NaN
row3 NaN NaN 5.0 6.0
row3
이 행추가 되었고 기존df
에는 없던 col2
과 col4
가 생성된것을 확인할 수 있습니다.
sort
인수를 사용하면 열을 사전적으로 정렬 할 수 있습니다.
print(pd.concat([df,df2],sort=True))
col1 col2 col3 col4
row1 1.0 NaN 2.0 NaN
row2 3.0 NaN 4.0 NaN
row3 NaN 5.0 NaN 6.0
ignore_index
인수를 사용하면 기존 index를 무시할 수 있습니다.
print(pd.concat([df,df2],sort=True,ignore_index=True))
col1 col2 col3 col4
0 1.0 NaN 2.0 NaN
1 3.0 NaN 4.0 NaN
2 NaN 5.0 NaN 6.0
verify_integrity인수의 사용
verify_integrity
인수를 True
로 설정하면 이름이 중복되는 인덱스가 존재할 경우 오류를 발생시킵니다.
먼저 중복되는 인덱스가 있는 2x2 객체를 하나 생성하겠습니다.
df3 = pd.DataFrame(data=[[7,8],[9,0]], index=['row2','row3'], columns=['col1','col3'])
print(df3)
>>
col1 col3
row2 7 8
row3 9 0
verify_integrity
가 False
일 경우 (기본값)
print(pd.concat([df,df3],verify_integrity=False))
>>
col1 col3
row1 1 2
row2 3 4
row2 7 8
row3 9 0
verify_integrity
가 True
일 경우
Copyprint(pd.concat([df,df3],verify_integrity=True))
>>
오류발생
---------------------------------------------------------------------------
NameError Traceback (most recent call last)
<ipython-input-57-5460e119f181> in <cell line: 0>()
----> 1 Copyprint(pd.concat([df,df3],verify_integrity=True))
NameError: name 'Copyprint' is not defined
turncate
메서드는 행이나 열에 대해서 앞뒤를 자르는 메서드 입니다.
df.truncate(before=None, after=None, axis=None, copy=True)
before
: 이 기준 이전을 삭제합니다.
after
: 이 기준 이후를 삭제합니다.
axis
: 자를 축 입니다.
copy
: 사본을 생성할지 여부입니다.
row = ['row1','row2','row3','row4']
col = ['col1','col2','col3','col4']
data = [[1,2,3,4],[5,6,7,8],[9,10,11,12],[13,14,15,16]]
df = pd.DataFrame(data=data, index=row, columns=col)
print(df)
>>
col1 col2 col3 col4
row1 1 2 3 4
row2 5 6 7 8
row3 9 10 11 12
row4 13 14 15 16
before
, after
, axis
를 이용하여 앞뒤를 잘라보겠습니다.
print(df.truncate(before='row2',after='row3',axis=0))
#행 자르기 (row2 이전, row3이후 자르기
col1 col2 col3 col4
row2 5 6 7 8
row3 9 10 11 12
print(df.truncate(before='col2',after='col3',axis=1))
#열 자르기 (col2 이전, col3이후 자르기)
col2 col3
row1 2 3
row2 6 7
row3 10 11
row4 14 15
drop_duplicates
메서드는 내용이 중복되는 행을 제거하는 메서드입니다.
subset
: 중복값을 검사할 열 입니다. 기본적으로 모든 열을 검사합니다.
keep
: {first / last} 중복제거를할때 남길 행입니다. first면 첫값을 남기고 last면 마지막 값을 남깁니다.
inplace
: 원본을 변경할지의 여부입니다.
ignore_index
: 원래 index를 무시할지 여부입니다. True
일 경우 0,1,2, ... , n으로 부여됩니다.
col = ['col1','col2','col3']
data = [['A','x','-'],['A','x','-'],['B','x','앞'],['B','y','-'],['B','y','뒤']]
df = pd.DataFrame(data=data, columns=col)
print(df)
>>
col1 col2 col3
0 A x -
1 A x -
2 B x 앞
3 B y -
4 B y 뒤
기본적인 사용법
subset
에 입력된 컬럼명을 기준으로 해당 컬럼의 중복값을 검사하게됩니다.
subset
이 따로 입력되지 않는 경우는 모든 열에대해 값이 중복인 행을 제거합니다.
Copyprint(df.drop_duplicates())
# 모든 요소가 중복인 0행과 1행중 1행이 삭제됨(처음값 남기는게 기본)
col1 col2 col3
0 A x -
2 B x 앞
3 B y -
4 B y 뒤
subset
에 특정 컬럼명만 입력할 경우, 해당 열에대해서만 중복값 검사를 수행합니다.
print(df.drop_duplicates(subset='col2'))
>>
col1 col2 col3 # col2에서 x와 y에대해서 중복값들 제거
0 A x -
3 B y -
subset
에 리스트를 입력할 경우 해당 열들에대해서 모두 중복인 경우만 삭제를 진행합니다.
print(df.drop_duplicates(subset=['col1','col2']))
>>
col1 col2 col3
0 A x -
2 B x 앞
3 B y -
keep인수를 통해 남길 행 선택
keep
인수를 통해서 중복값을 제거하고 남길 행을 선택할 수 있습니다.
keep='first'
인 경우 처음 값을 남깁니다. (기본값)
print(df.drop_duplicates(subset='col1',keep='first'))
>>
col1 col2 col3
0 A x -
2 B x 앞
keep='last'
인 경우 마지막 값을 남깁니다.
print(df.drop_duplicates(subset='col1',keep='last'))
>>
col1 col2 col3
1 A x -
4 B y 뒤
추가로 ignore_index=True
로 할 경우 결과값의 인덱스를 0, 1, 2, ... , n으로 설정합니다.
print(df.drop_duplicates(subset='col1',keep='last',ignore_index=True))
>>
col1 col2 col3 #인덱스가 0, 4에서 0, 1로 정리됩
0 A x -
1 B y 뒤
inplace 인수의 사용
Pandas 공통사항으로 inplace
인수를 사용할 경우 원본에 변경이 적용됩니다.
df.drop_duplicates(subset='col3',inplace=True)
print(df)
>>
col1 col2 col3
0 A x -
2 B x 앞
4 B y 뒤
squeeze
메서드는 차원을 축소(압축)하는 메서드입니다. 예를들어 한개의 행이나 열만 있는 DataFrame을 squeeze
하면 Series 객체가 되며, 1개 인덱스만 있는 Series를 squeeze
하면 스칼라값이 됩니다. 마찬가지로 1행,1열만 있는 DataFrame 객체를 squeeze
하면 스칼라 값이 됩니다.
axis
: 압축을 진행할 축 입니다.
df=pd.DataFrame(data=[[1,2],[3,4]],index=['row1','row2'],columns=['col1','col2'])
print(df)
>>
col1 col2
row1 1 2
row2 3 4
DataFrame을 Series로
1개의 열이나 1개의 행만 있는 DataFrame객체를 squeeze
하면 Series 객체가 됩니다.
먼저 row1
을 drop
하여 1행짜리 DataFrame을 만들고 squeeze
하겠습니다.
# row1 삭제
df_row=df.drop(index='row1')
print(df_row)
col1 col2
row2 3 4
# 압축 실행
print(df_row.squeeze())
#행을 축소한다
col1 3
col2 4
Name: row2, dtype: int64
결과값이 Series객체로 변환된 것을 확인할 수 있습니다.
col1
을 drop
하여 1열짜리 DataFrame을 만들고 squeeze
하겠습니다.
# col1 삭제
df_col=df.drop(columns='col1')
print(df_col)
col2
row1 2
row2 4
print(df_row.squeeze())
#행을 축소
col1 3
col2 4
Name: row2, dtype: int64
결과값이 Series객체로 변환된 것을 확인할 수 있습니다.
DataFrame을 스칼라 값으로 압축
col1
과 row1
을 삭제해서 요소1개짜리 DataFrame을 생성하고, squeeze
를 실행하면 스칼라값이 반환됩니다.
# row1 , col1을 삭제하여 1행/1열짜리 DataFrame만들기
df_col_row = df.drop(index='row1',columns='col1')
print(df_col_row)
col2
row2 4
print(df_col_row.squeeze())
>>
4
결과값으로 스칼라값이 반환된것을 확인할 수 있습니다.
압축할 수 없는 경우
압축할 수 없는경우 원본을 반환합니다.
print(df.squeeze())
>>
col1 col2
row1 1 2
row2 3 4
pivot
메서드는 데이터의 열을 기준으로 피벗테이블로 변환시키는 메서드 입니다.
index
: 인덱스로 사용될 열입니다.
columns
: 열로 사용될 열 입니다.
values
: 값으로 입력될 열 입니다.
※ index
나 columns
에 리스트를 입력 할 경우 멀티 인덱스로 피벗테이블이 생성됩니다.
values
에 리스트를 입력 할 경우 각 값에 대한 테이블이 연속적으로 생성됩니다.
col = ['Machine','Country','Price','Brand']
data = [['TV','Korea',1000,'A'],
['TV','Japan',1300,'B'],
['TV','China',300,'C'],
['PC','Korea',2000,'A'],
['PC','Japan',3000,'E'],
['PC','China',450,'F']]
df = pd.DataFrame(data=data, columns=col)
print(df)
Machine Country Price Brand
0 TV Korea 1000 A
1 TV Japan 1300 B
2 TV China 300 C
3 PC Korea 2000 A
4 PC Japan 3000 E
5 PC China 450 F
기본적인 사용법
index
를 Machine으로 columns
를 Country로, values
를 Price로 피벗 테이블을 생성해보겠습니다.
print(df.pivot(index='Machine',columns='Country',values='Price'))
Country China Japan Korea
Machine
PC 450 3000 2000
TV 300 1300 1000
values
값이 list
형태일 경우 피벗테이블이 옆쪽으로 연속으로 생성됩니다.
print(df.pivot(index='Machine',columns='Country',values=['Price','Brand']))
Price Brand
Country China Japan Korea China Japan Korea
Machine
PC 450 3000 2000 F E A
TV 300 1300 1000 C B A
참고로, values
를 따로 입력하지 않으면 남은 모든 열이 values
에 입력되어 연속으로 출력됩니다.
print(df.pivot(index='Machine',columns='Country')
Price Brand
Country China Japan Korea China Japan Korea
Machine
PC 450 3000 2000 F E A
TV 300 1300 1000 C B A
그 상태에서 [열 이름]
형태를 붙여서 원하는 values
만 출력할 수 있습니다.
print(df.pivot(index='Machine',columns='Country')['Brand'])
Country China Japan Korea
Machine
PC F E A
TV C B A
Multi index로 피벗 변환
index
나 columns
에 list
형태의 데이터를 입력할 경우 멀티 인덱스 형식으로 피벗 테이블이 생성됩니다.
index
가 list
형태일 경우
print(df.pivot(index=['Country','Machine'],columns='Brand',values='Price'))
Brand A B C E F
Country Machine
China PC NaN NaN NaN NaN 450.0
TV NaN NaN 300.0 NaN NaN
Japan PC NaN NaN NaN 3000.0 NaN
TV NaN 1300.0 NaN NaN NaN
Korea PC 2000.0 NaN NaN NaN NaN
TV 1000.0 NaN NaN NaN NaN
columns
가 list
형태일 경우
print(df.pivot(index='Country',columns=['Machine','Brand'],values='Price'))
Machine TV PC
Brand A B C A E F
Country
China NaN NaN 300.0 NaN NaN 450.0
Japan NaN 1300.0 NaN NaN 3000.0 NaN
Korea 1000.0 NaN NaN 2000.0 NaN NaN
피벗변환이 불가한 경우
중복값으로인해 피벗테이블의 생성이 불가능한 경우 오류를 반환합니다.
# 피벗화가 불가능한 중복값이 있는 객체 생성
df2 = pd.DataFrame(data=[['A','x',1],['A','x',2],['B','y',3],['B','z',4]],columns=['col1','col2','col3'])
print(df2
col1 col2 col3
0 A x 1
1 A x 2
2 B y 3
3 B z 4
# 피벗생성 시 오류 발생
print(df2.pivot(index='col1',columns='col2',values='col3'))
>>
오류발생
ValueError: Index contains duplicate entries, cannot reshape
pivot_table
메서드는 데이터를 스프레드시트 기반 피벗 테이블로 변환하는 메서드입니다.
엑셀 스프레드시트 피벗 테이블과 유사한 기능을 합니다.
values
: 값으로 입력될 열 입니다.
index
: 인덱스로 사용될 열입니다.
columns
: 열로 사용될 열 입니다.
aggfunc
: 결과로 출력될 함수 입니다.
fill_value
: 결측치를 채워넣을 값입니다.
margins
: 합계를 표시할지 여부입니다. True
일 경우 새 열을 생성하여 합계를 출력합니다.
dropna
: 항목이 모두 결측치인 열을 포함할지 여부입니다. 기본값은 True
로 포함하지 않습니다.
margins_name
: margins
가 True
일 경우 해당 열의 이름입니다.
observed
: 범주형 그룹에 대해 관찰된 값만 표시할지 여부 입니다.
sort
: 각 범주들을 사전적으로 정리할지 여부입니다. 기본값은 True
로 정렬이 수행됩니다.
col = ['Machine','Country','Grade','Price','Count']
data = [['TV','Korea','A',1000,3],
['TV','Korea','B', 800,8],
['TV','Korea','B', 800,2],
['TV','Japan','A',1300,5],
['TV','Japan','A',1300,1],
['PC','Korea','B',1500,6],
['PC','Korea','A',2000,9],
['PC','Japan','A',3000,3],
['PC','Japan','B',2500,3]]
df = pd.DataFrame(data=data, columns=col)
print(df)
Machine Country Grade Price Count
0 TV Korea A 1000 3
1 TV Korea B 800 8
2 TV Korea B 800 2
3 TV Japan A 1300 5
4 TV Japan A 1300 1
5 PC Korea B 1500 6
6 PC Korea A 2000 9
7 PC Japan A 3000 3
8 PC Japan B 2500 3
기본적인 사용법
index를 Machine
, Country
로 하고 columns를 Grade
로 설정하고 Count
값들을 np.sum
으로 합계를 계산하여 스프레드 시트로 출력해보겠습니다.
print(df.pivot_table(values='Count',index=['Machine','Country'],columns='Grade',aggfunc=np.sum))
# sum값으로 출력됨.
Grade A B
Machine Country
PC Japan 3.0 3.0
Korea 9.0 6.0
TV Japan 6.0 NaN
Korea 3.0 10.0
sort인수의 사용
결과는 기본적으로 사전적으로 정렬이 되어있습니다. PC와 TV, Japan과 Korea는 알파벳순서로 정렬되어있습니다.
sort
를 False
로하면 기존 입력 순서대로 출력이 됩니다.
print(df.pivot_table(values='Count',index=['Machine','Country'],columns='Grade',aggfunc=np.sum,sort=False))
Grade A B
Machine Country
TV Korea 3.0 10.0
Japan 6.0 NaN
PC Korea 9.0 6.0
Japan 3.0 3.0
여러 값에 대해 여러 함수 적용
엑셀의 피벗테이블과 유사하게 여러 값에 대해서 여러 값(values
)에 대해 여러 함수(aggfunc
)를 설정할 수 있습니다.
# list를 이용하여 다중 함수 적용이 가능합니다.
print(df.pivot_table(values=['Count','Price'],index=['Machine','Country'],columns='Grade',aggfunc=[np.sum,np.mean]))
sum mean
Count Price Count Price
Grade A B A B A B A B
Machine Country
PC Japan 3.0 3.0 3000.0 2500.0 3.0 3.0 3000.0 2500.0
Korea 9.0 6.0 2000.0 1500.0 9.0 6.0 2000.0 1500.0
TV Japan 6.0 NaN 2600.0 NaN 3.0 NaN 1300.0 NaN
Korea 3.0 10.0 1000.0 1600.0 3.0 5.0 1000.0 800.0
dict를 이용할 경우 각 값에 대해서 특정 함수의 적용이 가능합니다.
print(df.pivot_table(values=['Count','Price'],index=['Machine','Country'],columns='Grade',aggfunc={'Count':np.sum,'Price':np.mean}))
Count Price
Grade A B A B
Machine Country
PC Japan 3.0 3.0 3000.0 2500.0
Korea 9.0 6.0 2000.0 1500.0
TV Japan 6.0 NaN 1300.0 NaN
Korea 3.0 10.0 1000.0 800.0
fill_value를 이용한 결측치 제거
fill_value
에 값을 입력하므로서 결측치를 해당 값으로 대체할 수 있습니다.
print(df.pivot_table(values='Count',index=['Machine','Country'],columns='Grade',aggfunc=np.sum,fill_value='누락'))
Grade A B
Machine Country
PC Japan 3.0 3.0
Korea 9.0 6.0
TV Japan 6.0 누락
Korea 3.0 10.0
margines / margines_name 인수의 사용
margines
를 이용해서 총계를 출력할 수 있으며 margines_name
을 이용해서 해당 레이블의 이름을 지정할 수 있습니다.
print(df.pivot_table(values='Count',index=['Machine','Country'],columns='Grade',aggfunc=np.sum,margins=True))
Grade A B All
Machine Country
PC Japan 3.0 3.0 6
Korea 9.0 6.0 15
TV Japan 6.0 NaN 6
Korea 3.0 10.0 13
All 21.0 19.0 40
All
로 출력된 행/열의 이름을 변경해보겠습니다.
Copyprint(df.pivot_table(values='Count',index=['Machine','Country'],columns='Grade',aggfunc=np.sum,margins=True,margins_name='총계'))
Grade A B 총계
Machine Country
PC Japan 3.0 3.0 6
Korea 9.0 6.0 15
TV Japan 6.0 NaN 6
Korea 3.0 10.0 13
총계 21.0 19.0 40
melt
메서드는 피벗 형태의 DataFrame을 기존 형태로 해체하는 메서드입니다.
id_vars
: 기준이 될 열 입니다.
value_vars
: 기준열에 대한 하위 카테고리를 나열할 열을 선택합니다.
var_name
: 카테고리들이 나열된 열의 이름을 설정합니다.
value_name
: 카테고리들의 값이 나열될 열의 이름을 설정합니다.
col_leve
: multi index의 경우 melt
를 수행할 레벨을 설정합니다.
ignore_index
: 인덱스를 1,2,3, ... , n으로 설정할지 여부입니다. 기본적으로 True
로 1,2,3, ... , n으로 설정됩니다.
col = ['Country','Machine','Price','Brand']
data = [['Korea','TV',1000,'A'],
['Japan','TV',1300,'B'],
['Korea','PC',2000,'A'],
['Japan','PC',3000,'E']]
df = pd.DataFrame(data=data, columns=col)
print(df)
Country Machine Price Brand
0 Korea TV 1000 A
1 Japan TV 1300 B
2 Korea PC 2000 A
3 Japan PC 3000 E
Country
를 기준으로하여 Machine
과 Price
의 값을 하위 카데고리로 melt
를 수행해보겠습니다.
print(df.melt(id_vars='Country',value_vars=['Machine','Price']))
Country variable value
0 Korea Machine TV
1 Japan Machine TV
2 Korea Machine PC
3 Japan Machine PC
4 Korea Price 1000
5 Japan Price 1300
6 Korea Price 2000
7 Japan Price 3000
ignore_index
를 False로 할 경우 기존 인덱스를 사용하게 됩니다.
print(df.melt(id_vars='Country',value_vars=['Machine','Price'],ignore_index=False))
# 기존 인덱스를 사용한 것을 확인 할 수 있습니다.
Country variable value
0 Korea Machine TV
1 Japan Machine TV
2 Korea Machine PC
3 Japan Machine PC
0 Korea Price 1000
1 Japan Price 1300
2 Korea Price 2000
3 Japan Price 3000
var_name
과 value_name
을 지정함으로써 열 이름의 기본값인 variable
과 value
를 원하는 값으로 변경할 수 있습니다.
print(df.melt(id_vars='Country',value_vars=['Machine','Price'],var_name='Category',value_name='val'))
Country Category val
0 Korea Machine TV
1 Japan Machine TV
2 Korea Machine PC
3 Japan Machine PC
4 Korea Price 1000
5 Japan Price 1300
6 Korea Price 2000
7 Japan Price 3000
Multi-Index의 경우
Multi-Index(Multi-Columns)의 경우에는 인수들을 리스트-튜플로 설정하거나 col_level
을 지정해줌으로써 원하는대로 출력이 가능합니다.
먼저 기존의 Country
열을 좀더 세분화하여 Country-City
로 Multi-Columns을 생성해보겠습니다.
col2 = [['Area','Area','Value','Value','Value'],['Country','City','Machine','Price','Brand']]
data2 =[['Korea','Seoul','TV',1000,'A'],
['Japan','Tokyo','TV',1300,'B'],
['Korea','Jeju','PC',2000,'A'],
['Japan','Kyoto','PC',3000,'E']]
df2=pd.DataFrame(data=data2, columns=col2)
print(df2)
Area Value
Country City Machine Price Brand
0 Korea Seoul TV 1000 A
1 Japan Tokyo TV 1300 B
2 Korea Jeju PC 2000 A
3 Japan Kyoto PC 3000 E
이제 City
에대해서 Price
만 출력해보겠습니다.
하위 레벨에대해 출력할 경우 튜플을 이용해서 ('Area','City')로, ('Value','Price')로 세부설정을 입력하여 출력할 수 있습니다.
print(df2.melt(id_vars=[('Area','City')],value_vars=[('Value','Price')])
(Area, City) variable_0 variable_1 value
0 Seoul Value Price 1000
1 Tokyo Value Price 1300
2 Jeju Value Price 2000
3 Kyoto Value Price 3000
col_level
을 설정해 줄 경우 보다 간단하게 하위 카테고리의 출력이 가능합니다.
print(df2.melt(id_vars='City',value_vars='Price',col_level=1))
>>
City variable value
0 Seoul Price 1000
1 Tokyo Price 1300
2 Jeju Price 2000
3 Kyoto Price 3000
assign
메서드는 DataFrame에 새 열을 할당하는 메서드입니다.
할당할 새 열이 기존열과 이름이 같을경우 덮어씌워집니다.
kwargs
: 새열이름 = 내용
형식으로 입력되는 키워드입니다. 콤마(,
)를 통해 여러개를 입력할 수 있습니다.
df = pd.DataFrame(index=['row1','row2','row3'],data={'col1':[1,2,3]})
print(df)
>>
col1
row1 1
row2 2
row3 3
lambda
를 이용해 col1
에 +2
를 한 값으로 col2
를 생성해보겠습니다.
print(df.assign(col2=lambda x : x.col1+2))
>>
col1 col2
row1 1 3
row2 2 4
row3 3 5
lambda
를 사용하지 않고 아래와같이 새 열을 추가할 수 있습니다.
print(df.assign(col3=df['col1']*(-2)))
>>
col1 col3
row1 1 -2
row2 2 -4
row3 3 -6
동시에 여러열 할당
쉼표로 구분을 지으면서 여러개의 열을 할당할 수 있습니다.
print(df.assign(col2=lambda x : x.col1+2,col3=df['col1']*(-2)))
>>
col1 col2 col3
row1 1 3 -2
row2 2 4 -4
row3 3 5 -6
열이 중복될 경우
만약 추가할 새 열의 이름이 기존열과 중복된다면, 새 값으로 덮어씌워집니다.
print(df.assign(col1=[0,0,0]))
>>
col1
row1 0
row2 0
row3 0
replace
메서드는 객체 내 값을 다른 값으로 변경하는 메서드입니다.
to_replace
: 변경전 기존 값입니다.
value
: 변경될 값입니다.
inplace
: 원본을 변경할지 여부입니다.
limit
: method
사용시 변경 될 갯수 입니다.
regex
: regex 문법을 이용하여 변경값을 정합니다.
df = pd.DataFrame([[1,2,3], [4,5,6], [7,8,9]], index=['row1', 'row2', 'row3'], columns=['col1', 'col2', 'col3'])
print(df)
>>
col1 col2 col3
row1 1 2 3
row2 4 5 6
row3 7 8 9
기본적인 사용법
객체 전체에서 1을 99로 변경해보겠습니다.
print(df.replace(to_replace=1,value=99))
>>
col1 col2 col3 col4
row1 A w 99 alpha
row2 B x 2 beta
row3 C y 3 gamma
row4 D z 4 delta
to_replace
값이 list
형태이고 value
값이 단일값이면 전체가 동일하게 변경됩니다.
A
, B
, y
, z
를 -
로 변경해보겠습니다.
print(df.replace(to_replace=['A','B','y','z'],value='-'))
>>
col1 col2 col3 col4
row1 - w 1 alpha
row2 - x 2 beta
row3 C - 3 gamma
row4 D - 4 delta
to_replace
값과 value
값이 모두 같은 길이의 list
형태일 경우 각각 같은 순서의 값으로 변경됩니다.
A
, B
, y
, z
를 각각 a
, b
, Y
, Z
로 변경해보겠습니다.
print(df.replace(to_replace=['A','B','y','z'],value=['a','b','Y','Z']))
>>
col1 col2 col3 col4
row1 a w 1 alpha
row2 b x 2 beta
row3 C Y 3 gamma
row4 D Z 4 delta
method와 limit인수의 사용
method
가 ffill
일 경우 to_replace
값을 바로 위 값으로 변경하며, bfill
일 경우 to_replace
값을 바로 아래 값으로 변경합니다.
method
가 ffill
인 경우
print(df.replace(to_replace=['x','y'],method='ffill'))
>>
col1 col2 col3 col4 # x와 y를 바로 위의 값인 w로 변경
row1 A w 1 alpha
row2 B w 2 beta
row3 C w 3 gamma
row4 D z 4 delta
method
가 bfill
인 경우
print(df.replace(to_replace=['x','y'],method='bfill'))
>>
col1 col2 col3 col4 # x와 y를 바로 아래의 값인 z로 변경
row1 A w 1 alpha
row2 B z 2 beta
row3 C z 3 gamma
row4 D z 4 delta
method
인수를 사용할때 limit
인수를 통해 변경될 갯수를 지정할 수 있습니다. limit=1
을 통해 1개만 변경해보겠습니다.
print(df.replace(to_replace=['x','y'],method='bfill',limit=1))
>>
col1 col2 col3 col4 # x와 y에 대하여 bfill을 통해 아랫값인 z로 변경했으나 limit=1로 1개만 변경
row1 A w 1 alpha
row2 B x 2 beta
row3 C z 3 gamma
row4 D z 4 delta
dict형식의 사용
to_replace
에 dict
형태를 입력하여 value
값 설정 없이 변경이 가능합니다.
A
를 a
로, z
를 Z
로 변경해보겠습니다.
print(df.replace(to_replace={'A':'a','z':'Z'}))
>>
col1 col2 col3 col4
row1 a w 1 alpha
row2 B x 2 beta
row3 C y 3 gamma
row4 D Z 4 delta
dict
안에 dict
를 넣음으로써 특정 열의 특정값을 원하는 값으로 변경 할 수 있습니다.
col3
을 대상으로 1
을 -
로, 4
를 +
로 변경해보겠습니다.
print(df.replace(to_replace={'col3':{1:'-',4:'+'}}))
>>
col1 col2 col3 col4
row1 A w - alpha
row2 B x 2 beta
row3 C y 3 gamma
row4 D z + delta
dict
를 통해 각 열의 변경 원하는 값을 지정 후 value
를 통해 변경이 가능합니다.
col1
열에서 B
를, col2
열에서 w
를 100
으로 변경해보겠습니다.
print(df.replace(to_replace={'col1':'B','col2':'w'},value=100))
>>
col1 col2 col3 col4
row1 A 100 1 alpha
row2 100 x 2 beta
row3 C y 3 gamma
row4 D z 4 delta
regex의 사용
regex
를 사용할 경우 정규표현식으로 원하는 값을 지정해서 변경 할 수 있습니다.
to_replace
를 r'[e]'로 지정하고
value를
-로 하여 문자열에
e가 포함될 경우
-로 바꿔보겠습니다.
※이때 regex=True
로 해서 활성화를 진행해주어야 합니다.
print(df.replace(to_replace=r'[e]',value='-',regex=True))
>>
col1 col2 col3 col4
row1 A w 1 alpha
row2 B x 2 b-ta
row3 C y 3 gamma
row4 D z 4 d-lta
to_replace
를 사용하지 않고 단순히 regex
에 정규표현식을 입력하여도 동일한 결과를 얻을 수 있습니다.
print(df.replace(regex=r'[e]', value='-'))
>>
col1 col2 col3 col4
row1 A w 1 alpha
row2 B x 2 b-ta
row3 C y 3 gamma
row4 D z 4 d-lta
inplace를 통한 원본의 변경
Pandas 공통사항으로 inplcace=True
일 경우 원본을 변경하게 됩니다.
df.replace(regex=r'[e]', value='-',inplace=True)
print(df)
>>
col1 col2 col3 col4 # df를 출력함으로서 원본이 변경된것을 확인.
row1 A w 1 alpha
row2 B x 2 b-ta
row3 C y 3 gamma
row4 D z 4 d-lta
explode
메서드는 리스트형태의 값을 여러 행으로 전개하는 메서드 입니다.
column
: 전개할 리스트형태의 데이터가 있는 열 입니다.
ignore_index
: True일 경우 기존 인덱스를 무시하고 0,1,2, ... , n 형태의 인덱스로 변환됩니다.
data= [[[1,2,3],0,['a','b','c']],[4,[],3],[5,2,['x','y','z']]]
idx = ['row1','row2','row3']
col = ['col1','col2','col3']
df = pd.DataFrame(data = data, index = idx, columns = col)
print(df)
>>
col1 col2 col3
row1 [1, 2, 3] 0 [a, b, c]
row2 4 [] 3
row3 5 2 [x, y, z]
기본적인 사용법
리스트형태의 데이터가 있는 열을 지정함으로써 해당 리스트를 여러행으로 전개할 수 있습니다.
col1
열을 전개해보겠습니다.
print(df.explode('col1'))
>>
col1 col2 col3
row1 1 0 [a, b, c] # row1, col1의 [1,2,3]이 전개된 것을 확인할 수 있습니다.<br>
row1 2 0 [a, b, c]
row1 3 0 [a, b, c]
row2 4 [] 3
row3 5 2 [x, y, z]
빈 리스트의 경우 NaN
이 반환됩니다.
print(df.explode('col2'))
>>
col1 col2 col3
row1 [1, 2, 3] 0 [a, b, c]
row2 4 NaN 3 # 빈 리스트가 NaN으로 전개된것을 확인할 수 있습니다.<br>
row3 5 2 [x, y, z]
행에 여러개의 리스트 형태의 데이터가 있을 경우 모두 전개합니다.
print(df.explode('col3'))
>>
col1 col2 col3
row1 [1, 2, 3] 0 a
row1 [1, 2, 3] 0 b
row1 [1, 2, 3] 0 c
row2 4 [] 3
row3 5 2 x
row3 5 2 y
row3 5 2 z
여러 열을 동시에 전개할 경우
여러 열을 동시에 전개하려면 해당 열의 같은 행에 있는 리스트 형태의 데이터가 같은 길이를 가져야 합니다.
먼저, 해당 예시를 만족하는 데이터를 만들어 보겠습니다.
data = [[[1,2],['a','b']],[3,'c']]
idx = ['row1','row2']
col = ['col1','col2']
df = pd.DataFrame(data =data, index = idx, columns = col)
print(df)
>>
col1 col2
row1 [1, 2] [a, b]
row2 3 c
row1
에 같은 길이를 갖는 리스트 형태의 데이터가 있습니다.
print(df.explode(column=['col1','col2']))
>>
col1 col2
row1 1 a
row1 2 b
row2 3 c
ignore_index인수의 사용
ignore_index=True
인 경우 기존 인덱스는 무시되고 0, 1, 2, ... , n 형태의 인덱스로 변경됩니다.
print(df.explode(column=['col1','col2'],ignore_index=True))
>>
col1 col2
0 1 a
1 2 b
2 3 c
정말 유익한 정보예요!