dplyr로 데이터프레임 변형하기: 파이프와 핵심 동사
dplyr로 데이터프레임 변형하기: 파이프와 핵심 동사
데이터를 받아서 바로 원하는 그래프를 그릴 수 있는 경우는 드물어요. 대부분은 새 변수를 만들고, 행을 걸러내고, 순서를 바꾸는 작업을 먼저 해야 하죠. 이 페이지에서는 tidyverse의 핵심 패키지인 dplyr를 이용해 데이터프레임을 다루는 법을 배워볼게요. 파이프 연산자 |>를 함께 쓰면 복잡한 변형도 차례대로 읽어 내려갈 수 있어요.
본문
dplyr 동사의 공통점
dplyr의 동사(함수)들은 세 가지 공통점이 있어요. 첫째, 첫 번째 인자는 항상 데이터프레임이에요. 둘째, 그 뒤의 인자는 보통 변수 이름(따옴표 없이)으로 어떤 열을 다룰지를 말해줘요. 셋째, 결과물은 항상 새 데이터프레임이에요. 즉 기존 데이터를 바꾸는 게 아니라 새로운 걸 만들어 내죠.
파이프 연산자 (|>)
여러 동사를 이어 붙일 때 가장 많이 쓰는 게 파이프 |>예요. 왼쪽의 값을 오른쪽 함수의 첫 인자로 넘겨주는 역할을 해요.
x |> f(y)
# 는 f(x, y)와 같아요.
x |> f(y) |> g(z)
# 는 g(f(x, y), z)와 같아요.
실무에서는 파이프를 "그리고 나서(then)"라고 읽으면 코드가 자연스럽게 눈에 들어와요.
행을 다루는 동사
**filter()**는 조건에 맞는 행만 남겨요. 첫 인자는 데이터프레임, 그 뒤의 인자는 행을 남길 조건이에요. 출발 지연이 120분(2시간)을 넘긴 항공편만 골라볼게요.
flights |> filter(dep_delay > 120)
조건은 >(크다), >=(크거나 같다), <(작다), <=(작거나 같다), ==(같다), !=(같지 않다)를 써요. 여러 조건은 &나 ,로 "그리고", |로 "또는"을 나타내요.
# 1월 1일에 출발한 항공편
flights |> filter(month == 1 & day == 1)
# 1월 또는 2월에 출발한 항공편
flights |> filter(month == 1 | month == 2)
같은 변수의 여러 값을 비교할 땐 %in%이 편해요. 위의 "1월 또는 2월"은 아래처럼 짧게 쓸 수 있어요.
flights |> filter(month %in% c(1, 2))
**arrange()**는 행의 순서를 바꿔요. 오름차순이 기본이고, 내림차순은 desc()로 감싸면 돼요. filter()와 달리 어떤 행이 남느냐는 바뀌지 않고 순서만 달라져요.
dplyr 함수들은 입력을 절대 수정하지 않아요. 결과를 저장하려면 <-로 할당해야 해요.
jan1 <- flights |> filter(month == 1 & day == 1)
시작할 때 흔히 하는 실수 중 하나가 같은지 비교할 때 == 대신 =을 쓰는 거예요. filter()는 이걸 알아채고 오류를 알려줘요.
열을 다루는 동사
**mutate()**는 새 열을 만들어 데이터프레임에 붙이고, **select()**는 필요한 열만 골라내요. select()는 -를 붙이면 해당 열을 제외할 수도 있어요.
flights |>
mutate(gain = dep_delay - arr_delay) |>
select(dep_delay, arr_delay, gain)
그룹과 요약
**group_by()**로 행을 묶은 뒤 summarize()(영국식으론 summarise())로 집계하면 그룹별 요약값을 얻어요. n()은 현재 그룹의 행 수를 세는 특별한 요약 함수예요.
flights |>
group_by(month) |>
summarize(avg_delay = mean(dep_delay, na.rm = TRUE), n = n())
집계할 때는 항상 n()으로 행 수를 함께 넣는 습관이 좋아요. 표본이 너무 작은 데서 성급한 결론을 내지 않게 도와주거든요.
더 알아보기
- 조인으로 여러 데이터프레임을 연결하는 법은 Joins 페이지에서 다뤄요.
- 변수별 세부 도구(숫자, 문자열, 날짜 등)는 R for Data Science의 각 장에서 이어져요.
slice_*()계열 함수는 행의 위치로 행을 고를 때 써요.