Python-Pandas(1)

백동윤·6일 전

Python

목록 보기
16/17
post-thumbnail

04. Pandas

  • 파이썬 기반의 강력하고 사용하기 쉬운 데이터 분석 및 조작 라이브러리
import pandas as pd
import numpy as np
print(pd.__version__)

Pandas의 핵심 자료 구조

  • Series
  • DataFrame

Series

  • 인데스(라벨)가 붙은 1차원 배열
  • 인덱스 이름을 직접 지정할 수 있음

series 생성

  1. 리스트로 생성
data = [10, 20, 30, 40]
s = pd.Series(data)
print(s)
  1. 인덱스를 직접 지정
s = pd.Series(data, index = ["a", "b", "c", "d"])
print(s)
  1. 딕셔너리로 생성
data = {'서울':100, '부산':200, '대구':300}
s = pd.Series(data)
print(s)
  1. 하나의 값으로 series 생성
s = pd.Series(7, index = ["가", "나", "다"])
print(s)

시리즈의 주요 속성

data = [10, 20, 30, 40]
s = pd.Series(data, index = ["a", "b", "c", "d"], name = 'test data')
print("values: ", s.values) # 실제 데이터 배열
print("index: ", s.index) # 인덱스 객체
print("dtype: ", s.dtype) # 실제 데이터의 타입
print("size: ", s.size) # 데이터의 개수
print("shape: ", s.shape) # 배열의 형태
print("name: ", s.name) # series 이름

시리즈의 연산

s1 = pd. Series([10, 20, 30], index = ["a", "b", "c"])
s2 = pd.Series([5, 6, 7], index = ['c', 'b', 'd'])

result = s1 + s2

print(result)

브로드캐스팅

s = pd.Series([5, 10, 15])

print(s + 3)
print(s * 2)

불리언 연산 및 인덱싱

s = pd.Series([50, 60, 70, 80, 90, 100])

mask = s > 70
print(mask)
print(s[mask])
실습 1-1
s = pd.Series([5, 10, 15, 20])
print(s)

결과
0 5
1 10
2 15
3 20
dtype: int64

실습 1-2
s = pd. Series([90, 80, 85, 70], index = ["국어", "영어", "수학", "과학"])
print(s)

결과
국어 90
영어 80
수학 85
과학 70
dtype: int64

실습 1-3
data = {'서울':950, '부산':340, '인천':520}
s = pd.Series(data)
print(s["인천"])

결과
520

실습 1-4
s = pd.Series([1, 2 ,3, 4])
print("데이터 타입: ", s.dtype)

결과
데이터 타입: int64

실습 1-5
s1 = pd.Series([3, 5, 7], index=['a', 'b', 'c'])
s2 = pd.Series([10, 20, 30], index=['b', 'c', 'd'])

result = s1 + s2

print(result)

결과
a NaN
b 15.0
c 27.0
d NaN
dtype: float64

실습 1-6
s = pd.Series([1, 2, 3, 4, 5])
print(s + 10)

결과
0 11
1 12
2 13
3 14
4 15
dtype: int64

DataFrame

  • 2차원 라벨 데이터 구조
  • 시리즈를 모아놓은 것
  • 행과 열이 있고, 행과 열에 대해 라벨을 부여할 수 있음

DataFrame 생성

  1. 딕셔너리로 생성
data = {
    "이름": ['kim', 'lee', 'sim'],
    "나이": [15, 23, 44],
    "도시": ["서울", "부산", "대구"]

}

df = pd.DataFrame(data)
df
  1. 리스트의 리스트(2차원 리스트)로 생성
data = [[1, "a"], [2, "b"], [3, "c"]]
df = pd.DataFrame(data, columns = ["번호", "코드"])
df
  1. 딕셔너리의 리스트 생성
data = [
    {"이름": "동윤2", "나이": 26, "도시": "포항"},
    {"이름": "배칠수", "나이": 43, "도시": "서울"}
]

df = pd.DataFrame(data, index = ["a", "b"])
df
  1. 시리즈의 딕셔너리로 생성
s1 = pd.Series(["국어", "수학", "영어"], index = ["a", "b", "c"])
s2 = pd.Series([100, 90, 80], index = ["a", "b", "c"])

df = pd.DataFrame({"과목": s1, "점수": s2})
df

데이터 프레임 기본 속성

data = [
    {"이름": "동윤2", "나이": 26, "도시": "포항"},
    {"이름": "배칠수", "나이": 43, "도시": "서울"}
]

df = pd.DataFrame(data)

print("shape", df.shape)
print("columns", df.columns)
print("index", df.index)
print("dtypes", df.dtypes)
print("value", df.values)
print("info", df.info())
실습 2-1
data = [
    {"이름": "홍길동", "나이": 28, "도시": "서울"},
    {"이름": "김철수", "나이": 33, "도시": "부산"},
    {"이름": "이형의", "나이": 25, "도시": "대구"}
]

df = pd.DataFrame(data)
df

결과
이름 나이 도시
0 홍길동 28 서울
1 김철수 33 부산
2 이형의 25 대구

실습 2-2
data = {'A': [1, 2, 3], 'B': [4, 5, 6]}
df = pd.DataFrame(data)
df

결과
A B
0 1 4
1 2 5
2 3 6

실습 2-3
data = [{'과목': '수학', '점수': 90}, {'과목': '영어', '점수': 85}, {'과목': '과학', '점수': 95}]
df = pd.DataFrame(data)
df

결과
과목 점수
0 수학 90
1 영어 85
2 과학 95

실습 2-4
data = {'이름': ['민수', '영희', '철수'], '점수': [80, 92, 77]}

df = pd.DataFrame(data, index = ["학생1", "학생2", "학생3"])
df

결과
이름 점수
학생1 민수 80
학생2 영희 92
학생3 철수 77

실습 2-5
kor = pd.Series([90, 85, 80], index=['a', 'b', 'c'])
eng = pd.Series([95, 88, 82], index=['a', 'b', 'c'])

df = pd.DataFrame({"국어 점수?": kor, "영어 점수?": eng})
df

결과
국어 점수? 영어 점수?
a 90 95
b 85 88
c 80 82

실습 2-6
data = {'A': [1, 2], 'B': [3,4]}
df = pd.DataFrame(data, index = ['B', 'A'])
df

결과
A B
B 1 3
A 2 4

실습 2-7
data = [['펜', 1000, 50], ['노트', 2000, 30]]
df = pd.DataFrame(data, columns=['product', 'price', 'stock'])
df

결과
product price stock
0 펜 1000 50
1 노트 2000 30

실습 2-8
data = {'국가': ['한국', '일본', '미국'], '수도': ['서울', '도쿄', '워싱턴']}
df = pd.DataFrame(data)
print("국가", df.values[:,0])
print("국가", df["국가"])

결과
국가 ['한국' '일본' '미국']
국가 0 한국
1 일본
2 미국
Name: 국가, dtype: object

데이터 탐색과 요약

data = {
    "이름": ["홍길동", "이순신", "김유신", "강감찬", "장보고", "이방원"],
    "나이": [23, 35, 31, 40, 28, 34],
    "직업": ["학생", "군인", "장군", "장군", "상인", "왕자"]
}
df = pd.DataFrame(data)
df

# 데이터 앞부분 미리보기: head(n)
# 기본값 n = 5
df.head()
df.head(3)

# 데이터 뒷부분 미리보기: tail(n)
# 기본값 n = 5
df.tail()
df.tail(2)

# info()
df.info()

# describe()
df.describe() # 기본적으로 수치형 컬럼만 요약
df.describe(include = "object")
df.describe(include = "all")

인덱싱과 슬라이싱

  • 인덱싱: 컬럼에 대해 인덱싱 적용
  • 특정 컬럼(시리즈) 선택
df["이름"]

# 여러 컬럼을 리스트로 선택
df[['이름', '나이']]

# .으로도 조회가 가능함
df.이름
# 슬라이싱
df[1:4]
df[-3:]

# 슬라이싱은 행 기준으로 동작, 열 기준은 별도의 방법을 사용
# df[:, 0: 2]

iloc, loc

# iloc
# Integer Location
# 정수 위치 기반의 인덱싱, 슬라이싱
# numpy의 슬라이싱과 거의 유사함

# 단일 행/열 선택
df.iloc[0] # 첫 번째 행
df.iloc[:, 1] # 두 번째 열

# 여러 행/열 동시 선택
df.iloc[1:4]
df.iloc[:, 0:2]
df.iloc[1:4, 0:2]

# Fancy Indexing
df.iloc[[0,2,4]]
df.iloc[:, [1, 2]]
df.iloc[[0, 2, 4], [1, 2]]

# 음수 인덱스 슬라이싱
df.iloc[-1]
df.iloc[:, -2:]

# loc
# Location의 약자
# 라벨의 이름 기준으로 인덱싱/슬라이싱
# 단일 행/열 선택
# 시작과 끝을 모두 포함
# 음수 인덱스 사용 X

df.loc[0]
df.loc[:, "이름"]
# 여러 행/열 선택
df.loc[2:4, ["이름", "직업"]]
df.loc[2:4, "이름": "직업"]

# 조건식
mask = df["나이"] >= 30
df.loc[mask, ["이름", "나이"]]
# 컬럼을 인덱스로 지정
df2 = df.set_index("이름")
df2
실습 3
df2.loc["이순신"]
data = {
"이름": ["홍길동", "이순신", "김유신", "강감찬", "장보고", "이방원", "최무선", "정도전"],
"나이": [23, 35, 31, 40 , 28, 34 , 42, 29],
"직업": ["학생", "군인", "장군", "장군", "상인", "왕자", "과학자", "정치가"],
"점수": [85, 90, 75, 88, 92, 95, 87, 83]
}
df = pd.DataFrame(data)
df
실습 3-1
df.iloc[2:5, 1:3]

결과

나이 직업
2 31 장군
3 40 장군
4 28 상인

실습 3-2
df.loc[3:6, ["이름", "점수"]]

결과

이름 점수
3 강감찬 88
4 장보고 92
5 이방원 95
6 최무선 87

실습 3-3
df.iloc[-3:, 2:4]

결과
직업 점수
5 왕자 95
6 과학자 87
7 정치가 83

실습 3-4
df.iloc[[1, 3, 5, 7], :]

결과

이름 나이 직업 점수
1 이순신 35 군인 90
3 강감찬 40 장군 88
5 이방원 34 왕자 95
7 정도전 29 정치가 83

실습 3-5
df.loc[4:7, ["나이", "점수"]]

결과

나이	점수

4 28 92
5 34 95
6 42 87
7 29 83

실습 3-6
df.iloc[[0, 2, 4, 6], [0, 2]]

결과

이름	직업

0 홍길동 학생
2 김유신 장군
4 장보고 상인
6 최무선 과학자

통계함수(집계함수)

data = {
    "상품명": ["무선 이어폰", "스마트 워치", "텀블러", "노트북", "블루투스 스피커", "무드등"],
    "가격": [129000, 250000, 15000, 1200000, 85000, 22000],
    "재고": [23, 12, 54, 5, 17, 31]
}
df = pd.DataFrame(data)
df
df.describe()

# 평균
df["가격"].mean()

# 중강값
df["재고"].median()

# 표준편차
df["가격"].std()
df["재고"].std()

# 분산
df["재고"].var()

# 값의 개수
df["상품명"].count()

# 최댓값
df["가격"].max()

# 최솟값
df["재고"].min()

# 합계
df["가격"].sum()
# 쵀댓값의 위치와 최소값의 위치
df.idxmax()

df.idxmin()
df["가격"].idxmin()

결측값 처리

  • 결측값: 값이 기록되지 않은 상태의 데이터
  • NaN(Not a Number)
data = {
    "이름": ["서준", "하은", "민준", "서연", "이안", "지민"],
    "나이": [22, 28, np.nan, 31, 27, 24],
    "점수": [89, np.nan, 83, 90, 88, 93]
}
df = pd.DataFrame(data)
df
# 결측값 탐지
# isnull: 결측값이 맞으면 True 아니면 False
df.isnull()

# 각 컬럼의 결측값의 수 계산
df.isnull().sum()

# 데이터의 전체 결측값 수 계산
df.isnull().sum().sum()

# notnull 결측값이 아니면 True, 맞으면 False
df.notnull()

# dropna 결측값이 있는 행 삭제
df2 = df.dropna()
df2

# 결측값이 있는 열 삭제
df3 = df.dropna(axis = 1)
df3

# fillna 결측값을 특정 값으로 대체
df4 = df.fillna(0)
df4
avg_age = df["나이"].mean()
avg_age

df["나이"] = df["나이"].fillna(avg_age)
df

# 이전 값으로 결측값 채우기 (forward fill)
df5 = df.ffill()
df5

# 뒤의 값으로 결측값 채우기 (backward fill)
df6 = df.bfill()
df6
실습 4
data = {
"도시": ["서울", "부산", "광주", "대구", np.nan, "춘천"],
"미세먼지": [45, 51, np.nan, 38, 49 , np.nan],
"초미세먼지": [20, np.nan, 17, 18, 22, 19],
"강수량": [0.0, 2.5, 1.0, np.nan, 3.1, 0.0]
}
df = pd.DataFrame(data)
실습 4-1
print(df["미세먼지"].mean())
print(df["미세먼지"].median())

결과

45.75
47.0

실습 4-2
print(df["초미세먼지"].max())
print(df["초미세먼지"].min())

결과

22.0
17.0

실습 4-3
print(df.isnull().sum())

결과

도시 1
미세먼지 2
초미세먼지 1
강수량 1
dtype: int64

실습 4-4
df2 = df.dropna()
print(df2["초미세먼지"].mean)

결과

<bound method Series.mean of 0 20.0
Name: 초미세먼지, dtype: float64>

실습 4-5
df3 = df.fillna(0)
print(df3["미세먼지"].sum())
print(df3["초미세먼지"].sum())

결과

183.0
96.0

실습 4-6
avg_val = df["미세먼지"].mean()
avg_val

df["미세먼지"] = df["미세먼지"].fillna(avg_val)
print(df["미세먼지"].std())

결과

4.444097208657794

profile
동윤2입니다.

0개의 댓글