학습일지

[스나이퍼팩토리] 한컴AI아카데미(26.06.17) Pandas

cd-record 2026. 6. 17. 18:13

 


Pandas

Pandas이란?

  • Pandas는 파이썬에서 데이터 작업에 사용되는 라이브러리로 데이터 분석, 정리, 탐색, 조작을 위한 기능이 포함되어 빅데이터 분석은 물론 통계 이론에 기반한 데이터 분석이 가능합니다.

1. 데이터 구조(Data Structures)

  • Series(시리즈): 1차원 배열로, 인덱스(Index)와 값(Value)으로 구성, 하나의 열(Column)데이터라고 생각
  • DataFrame(데이터 프레임): 2차원 표 구조, 여러 개의 시리즈가 모여 만들어지며, 행(Row), 열(Column)로 구성된 데이터 분석의 기본 단위

2. 주요 기능

  • 데이터 입출력: CSV, Excel, SQL, JSON 등 다양한 형식의 파일을 쉽게 읽고(read) 쓸(to) 수 있습니다.
    파일형식 Reader Writer
    CSV read_csv to_csv
    EXCEL read_excel to_excel
    HTML read_html to_html
    JSON read_json to_json
    SQL read_sql to_sql
  • 데이터 정제 (Data Cleaning): 결측치(NaN/None)를 찾아 삭제하거나 다른 값으로 채우고, 데이터 타입을 변경하는 등 복잡한 전처리가 가능합니다.
  • 데이터 선택 및 필터링: 특정 행이나 열을 선택하고, 조건문을 사용하여 원하는 데이터만 빠르게 추출. 즉,  정제되지 않은 데이터를 정리하여 가독성과 연관성이 높은 데이터로 만들 수 있습니다.
  • 데이터 병합 및 재구조화: 여러 데이터를 하나로 합치거나(Merge/Join), 피벗 테이블(Pivot Table)을 만들어 데이터를 원하는 형태로 변환할 수 있습니다.
  • 데이터 집계 (Grouping): 데이터를 특정 기준으로 그룹화하여 합계, 평균, 개수 등을 계산하는 연산에 탁월합니다.

3.  작업 흐름

 

  • 로드 (Load): 외부 데이터 파일을 불러옵니다. (pd.read_csv())
  • 탐색 (Explore): 데이터의 형태나 요약 정보를 확인합니다. (df.head(), df.info(), df.describe())
  • 전처리 (Clean/Transform): 불필요한 데이터를 지우거나 값을 보정합니다. (df.dropna(), df.rename())
  • 분석 (Analyze): 통계량을 계산하거나 그룹별 연산을 수행합니다. (df.groupby().mean())
  • 저장/출력 (Visualize/Export): 분석 결과를 파일로 저장하거나 시각화 도구(Matplotlib, Seaborn 등)와 연동합니다.

 

설치

pip install pandas

사용

import pandas as pd

Series(시리즈)

기본 구조(하나의 컬럼 데이터)

city = ['서울','부산','울산']
df = pd.Series(city)
'''
0    서울
1    부산
2    울산
dtype: str
'''

 

인덱싱

# 인덱스 변경 ( 0, 1, 2 -> a, b, c)
df = pd.Series(city, index = ['a','b','c'])
print(df)
print(df['a'])

# 시리즈 생성
city = {'서울': 940, '부산':330, '울산':110}
df = pd.Series(city)
print(df)
print(df['부산'])

# 시리즈 생성2
data = [10, 20, 30, 40]
index = ['a','b','c','d']
series = pd.Series(data, index=index)
print(series)

기본 통계량 계산 및 기본 명령

print("Mean:", series.mean()) # 평균
print("Sum:", series.sum()) # 합계
print("Max:", series.max()) # 최댓값
print("Standard Deviation:", series.std()) # 표준편차

series['c'] # 인덱스'c'(위치)에 있는 원소

series > 20 # 조건 지정
'''
a    False
b    False
c     True
d     True
e     True
dtype: bool
'''

series[series > 20] # 조건에 맞는 값만 가져오기

series['c'] = 100 # 원소 수집(원소가 이미 있을 때)

series['e'] = 50 # 원소 추가(원소가 없을 때)

series = series.drop('a') # 원소 삭제
'''
b     20
c    100
d     40
e     50
dtype: int64
'''

인덱스 정렬 및 자동 매칭

data2 = [5, 15, 25, 35]
series2 = pd.Series(data2, index=['b','c','d','e'])

result = series + series2
print(result)
'''
b     25
c    115
d     65
e     85
dtype: int64
'''

 

  • 핵심 원리: 판다스는 연산을 수행할 때 데이터의 위치(순서)가 아니라 인덱스(Index) 이름을 기준으로 값을 찾아 더합니다.
  • 결과 분석:
    • 두 시리즈에 공통으로 존재하는 인덱스(b, c, d)는 값을 서로 더합니다.
    • 만약 한쪽에만 존재하는 인덱스(a는 series에만 있음, e는 series2에만 있음)는 더할 상대가 없으므로 결측값인 NaN (Not a Number)으로 처리됩니다.
    • 결과: a: NaN, b: 25, c: 45, d: 65, e: NaN 순으로 출력됩니다.

시계열 데이터 생성

date_range = pd.date_range(start='2023-01-01', periods=5)
print(date_range)
'''
DatetimeIndex(['2023-01-01', '2023-01-02', '2023-01-03', '2023-01-04',
               '2023-01-05'],
              dtype='datetime64[us]', freq='D')
'''

 

 

  • 핵심 원리: pd.date_range는 지정된 시작일로부터 규칙적인 간격(기본값은 일 단위)으로 날짜 인덱스를 자동으로 생성합니다.
  • 결과 분석: '2023-01-01'부터 시작하여 5일간의 날짜(2023-01-01 ~ 2023-01-05)를 가진 DatetimeIndex 객체가 생성됩니다. 이는 단순히 날짜 텍스트 리스트가 아니라, 날짜 계산이 가능한 전문 객체입니다.

시계열 데이터 다루기

time_series = pd.Series([1,3,5,7,9], index=date_range)
print(time_series)
print(time_series['2023-01-02'])
'''
2023-01-01    1
2023-01-02    3
2023-01-03    5
2023-01-04    7
2023-01-05    9
Freq: D, dtype: int64
3
'''

 

  • 핵심 원리: 시간 인덱스를 활용하면 문자열 형태의 날짜로 직접 데이터에 접근할 수 있습니다. 굳이 인덱스 번호(0, 1, 2...)를 기억할 필요가 없습니다.
  • 결과 분석:
    • time_series['2023-01-02']와 같이 날짜 문자열을 넣어 호출하면, 해당 날짜에 대응하는 값인 3이 바로 반환됩니다.
    • 이는 데이터 분석 시 "2023년 1월 2일의 매출이 얼마야?"와 같은 질문에 매우 직관적으로 답할 수 있게 해줍니다.

** dtype, freq

1. dtype (Data Type, 데이터 타입)

 

  • 왜 중요한가요? 파이썬의 리스트와 달리, 판다스 시리즈는 모든 요소가 동일한 데이터 타입을 가져야 합니다. 타입이 정해져 있어야 컴퓨터가 메모리를 효율적으로 쓰고 연산을 빠르게 수행할 수 있기 때문입니다.
  • 주요 예시:
    • int64: 정수형 (64비트)
    • float64: 실수형 (소수점이 있는 숫자)
    • object: 문자열(String)이거나 여러 타입이 섞여 있을 때 주로 나타남
    • datetime64[ns]: 날짜와 시간 정보

2. freq (Frequency, 빈도)

 

  • 왜 중요한가요? 데이터가 일정한 간격(매일, 매달, 매시간 등)으로 기록되었음을 판다스가 인지하고 있다는 뜻입니다. 이 정보를 알면 나중에 데이터를 리샘플링(Resampling)하거나 미래 날짜를 예측할 때 매우 유용합니다.
  • 주요 예시:
    • freq='D': Day, 하루 단위
    • freq='M': Month, 월 단위
    • freq='H': Hour, 시간 단위
    • freq='MS': Month Start, 월 시작일

 

DataFrame(데이터 프레임)

기본구조

import pandas as pd
city = {
	'도시': ['서울','부산','울산'],
	'인구': [940,330,110]
}

df = pd.DataFrame(city)
df

'''
	도시	인구
0	서울	940
1	부산	330
2	울산	110
'''

 

 

 

데이터프레임으로 변환

df = time_series.to_frame(name='Values')
# name = columns 하지만 to_frame()메서드에서는 columns라는 파라미터 존재 X
print(df)

.loc VS .iloc

구분 .loc (Label-based) .iloc (Integer-based)
기준 **이름(Label)**으로 접근 **순서(Index 번호)**로 접근
슬라이싱 끝점 포함 (0:2 → 0, 1, 2) 끝점 미포함 (0:2 → 0, 1)
상황 인덱스 이름이나 컬럼명을 알 때 데이터의 몇 번째인지 위치를 알 때
  • .loc[행]: 인덱스 이름(Label)로 지정 (숫자 또는 문자, index 아님 주의)
    • df.loc[0] # 시리즈 형태
    • df.loc[[0]] # 데이터프레임 형태
    • df.loc[[0,1,3]] # 여러 행을 한꺼번에 보려면 대괄호를 포함
    • df.loc[0:3] # 슬라이싱을 이용할 때는 대괄호 제거
      • df.loc[0:3] # 0~3번 레이블까지를 의미 -> 4개의 데이터를 보여준다 (0, 1, 2, 3)
      • df.iloc[0:3] # 0~3 index까지를 의미 -> 3개의 데이터를 보여준다. (0, 1, 2)
  • .loc[행, 열]
    • df.loc[0, '성명'] # 시리즈 형태
    • df.loc[[0],['성명']] # 데이터프레임 형태 (복수 개 사용시에는 반드시 대괄호 필요)
    • df.loc[0:3, ['성명','급여']]
    • df.loc[0:3, '성명':'급여'] # 슬라이싱 사용시 대괄호 반드시 제거
  • .loc[조건, 열]
    • df.loc[df['급여']>=50000000] # '급여'컬럼의 데이터에서 5백만원 이상인 행
    • df.loc[df['급여']>50000000, ['성명']] # '급여' 컬럼의 데이터에서 5백만원 이상인 행에 대해 '성명' 컬럼만
    • 파생 데이터 생성
      • df['체질량']=''" # 새로운 '체질량'이라는 빈 컬럼(열) 추가
      • df.loc[df['몸무게']>80, ['체질량']] = '비만' #몸무게' 컬럼의 데이터에서 80이상인 행을 추출한 다음, 해당 행에 대해서만 '체질량' 컬럼에 '비만'을 입력
  • .iloc
    • .loc와 형식은 동일한데 loc달리 행과 컬럼의 index 정보로만 접근

인덱싱으로

df.iloc[[0,2], [0,3]]
df.iloc[:3, :2]

복사

df2 = df.copy() # 원본 유지하면서 작업을 할 때 반드시 복사해서 작업
df['나이'] > 40
df[df['나이'] > 40]
df[df['나이'] > 40].index

df.drop( 행 인텍스 레이블), df.drop(행, 열 인덱스, axis) # axis 생략 시 기본값은 0

df3 = df.drop(0) # 원본 삭제 x

df3.drop(['몸무게'], axis=1) # axis=0 은 행, axis=1 은 열
df.drop(df[df['나이'] > 40].index) # 특정 조건에 맞는 행만 삭제
import pandas as pd

data = ['김예찬, m, 부장, 010-1234-5678, 서울시 강남구 삼성동',
'이하은, f, 인턴, 010-8765-4321, 부산시 해운대구 우동',
'박지현, f, 과장, 010-1357-2468, 대구시 수성구 범어동',
'최준호, m, 임시, 010-1928-3746, 인천시 연수구 송도동',
'김예서, f, 과장, 010-2846-5937, 천안시 서북구 두정동']

df = pd.DataFrame(data,columns=['직원데이터'])
df = df['직원데이터'].str.split(',',expand=True)
# expand=False(기본값): 결과를 '리스트' 형태로 반환
# exapnd=True: 결과를 '데이터프레임' 형태로 반환

df.columns = ['이름','성별','직급','전화번호','주소']
# df['성별'].str.replace('M','Male') # 수정된 새로운 결과물을 반환하기 때문에 새로운 변수에 저장
df['성별']=df['성별'].str.upper()
df['성별']=df['성별'].str.replace('M','Male')
df['성별']=df['성별'].str.replace('F','Female')
df['성별']=df['성별'].str.replace('Male','남성').str.replace('Female','여성')
df

df['직급'].unique() # 하나만 있는 값 확인
df['직급'] = df['직급'].str.replace('인턴|임시','사원', regex=True)

df

df['직급'].unique()
df['주소'] = df['주소'].str.strip() # 양끝 공백 제거
df[['시','구','동']] = df['주소'].str.split(' ', expand=True)
df.drop(['주소'], axis=1) #열 제거

regex=True의 역할

코드에서 사용하신 '인턴|임시' 부분에서 | (파이프) 기호가 바로 핵심입니다.

  • | 기호의 의미: 파이썬이나 정규식에서 '또는(OR)'을 의미합니다.
  • 즉, '인턴|임시'는 "인턴이거나, 혹은 임시인 글자를 찾아라"라는 뜻입니다.
  • regex=True를 설정하면 판다스는 이 '|'를 단순한 문자가 아니라 '논리 연산자'로 인식하여, 해당 패턴에 맞는 모든 단어를 '사원'으로 바꿔줍니다.
  • 정규식 패턴 예시
    패턴 의미 활용 예시
    ^A A로 시작하는 문자열 ^김 (김씨로 시작하는 사람)
    A$ A로 끝나는 문자열 님$ (님으로 끝나는 이름)
    [0-9] 숫자 0부터 9까지 숫자만 포함된 데이터 필터링
    . 아무 글자 하나 패턴의 중간 글자 생략 시

 

 

 

 

 

 

 

——————————————————————————

본 후기는 [한글과컴퓨터x한국생산성본부x스나이퍼팩토리] 한컴 AI 아카데미 (B-log) 리뷰로 작성 되었습니다.