본문 바로가기
C.W.K.
Stream
Lesson 04 of 06 · published

CSV — 쉼표로 나누면 안 되는 표 형식

~18 min · csv, dictreader, dictwriter, quoting

Level 0호기심
0 XP0/93 lessons0/23 achievements
0/100 XP to next level100 XP to go0% complete

행을 리스트로 볼지 딕셔너리로 볼지

reader/writer는 행을 리스트로, DictReader/DictWriter는 머리글을 키로 한 딕셔너리로 다뤄. 열 순서보다 이름이 계약이라면 딕셔너리 형태가 읽기 좋아.

항상 newline=''로 열어

csv 모듈이 파일 안의 줄바꿈과 따옴표를 직접 처리해야 하므로 텍스트 층의 줄바꿈 변환을 꺼. 그렇지 않으면 Windows의 빈 행이나 여러 줄 셀 오류가 생길 수 있어.

따옴표가 셀 안의 쉼표와 줄바꿈을 지켜

직접 split하지 말고 모듈에 맡겨. 구분자와 따옴표가 다른 파일은 dialect를 지정하거나 표본으로 추정하되, CSV에는 타입과 필수 열을 보장하는 스키마가 없으므로 읽은 뒤 경계에서 검증해.

Code

DictReader로 행을 딕셔너리로 읽기·python
import csv
import io

data = '''name,age,role
alice,30,admin
bob,25,member
charlie,35,member'''

# 데모용 문자열 읽기, 파일 객체와도 같음
reader = csv.DictReader(io.StringIO(data))
for row in reader:
    print(row)
# {'name': 'alice', 'age': '30', 'role': 'admin'}
# {'name': 'bob', 'age': '25', 'role': 'member'}
# {'name': 'charlie', 'age': '35', 'role': 'member'}

# 주의 — 모든 값이 문자열, 필요 시 수동 변환
rows = list(csv.DictReader(io.StringIO(data)))
for row in rows:
    row["age"] = int(row["age"])
DictWriter로 딕셔너리 행 쓰기·python
import csv
import io

rows = [
    {"name": "alice", "age": 30, "role": "admin"},
    {"name": "bob", "age": 25, "role": "member"},
]

buf = io.StringIO()
writer = csv.DictWriter(buf, fieldnames=["name", "age", "role"])
writer.writeheader()
writer.writerows(rows)

print(buf.getvalue())
# name,age,role
# alice,30,admin
# bob,25,member
newline을 비운 채 파일 열기·python
import csv

# Python CSV 파일엔 항상 newline=''
with open("/tmp/users.csv", "w", newline="", encoding="utf-8") as f:
    writer = csv.DictWriter(f, fieldnames=["name", "age"])
    writer.writeheader()
    writer.writerow({"name": "alice", "age": 30})
    writer.writerow({"name": "bob", "age": 25})

with open("/tmp/users.csv", newline="", encoding="utf-8") as f:
    for row in csv.DictReader(f):
        print(row)
쉼표와 따옴표가 든 셀 처리하기·python
import csv
import io

rows = [
    {"name": "alice", "note": "hello, world"},          # 콤마 있음
    {"name": "bob", "note": 'she said "hi"'},          # 따옴표
    {"name": "charlie", "note": "line1\nline2"},        # 줄바꿈
]

buf = io.StringIO()
writer = csv.DictWriter(buf, fieldnames=["name", "note"])
writer.writeheader()
writer.writerows(rows)

print(buf.getvalue())
# name,note
# alice,"hello, world"
# bob,"she said ""hi"""           — 리터럴 따옴표는 더블
# charlie,"line1
# line2"                            — 줄바꿈 때문에 quote

# csv 가 다 처리. CSV 손으로 쓰지 마.
TSV처럼 다른 dialect 다루기·python
import csv
import io

data = '''name\tage\trole
alice\t30\tadmin
bob\t25\tmember'''

# 탭 구분 — delimiter 변경
for row in csv.DictReader(io.StringIO(data), delimiter="\t"):
    print(row)

# csv.Sniffer 가 추측
sniffer = csv.Sniffer()
dialect = sniffer.sniff(data[:200])
print("검출된 delimiter:", repr(dialect.delimiter))

External links

Exercise

title, author, year, price를 가진 책 세 권을 DictWriter와 newline=''로 /tmp/books.csv에 써. 제목 하나에는 쉼표, 하나에는 Unicode 문자를 넣어. DictReader로 다시 읽고 문자열로 돌아온 숫자를 변환해 원본과 같은지 확인해.

Progress

Progress is local-only — sign in to sync across devices.
이 페이지에서 버그를 발견하셨거나 피드백이 있으세요?문제 신고

댓글 0

🔔 답글 알림 (로그인 필요)
로그인 — 댓글을 남기려면 로그인해 주세요.

아직 댓글이 없어요. 첫 댓글을 남겨보세요.