iBetter Books
수정

tidyverse 핵심 (dplyr, tidyr)

Shiny 앱의 서버 코드에서 데이터를 필터링하고 변환하는 작업이 자주 필요합니다. tidyverse의 dplyr과 tidyr은 이 작업을 직관적으로 처리할 수 있게 해줍니다.

library(tidyverse)

dplyr 핵심 함수

dplyr의 핵심 함수 다섯 가지를 알면 대부분의 데이터 처리가 가능합니다.

실습에 사용할 데이터를 준비합니다.

students <- tibble(
  name = c("Alice", "Bob", "Charlie", "Diana", "Eve"),
  dept = c("통계", "수학", "통계", "컴퓨터", "수학"),
  score = c(85, 92, 78, 95, 88),
  year = c(2, 3, 1, 4, 2)
)

filter() — 행 필터링

조건에 맞는 행만 선택합니다.

# 90점 이상인 학생
filter(students, score >= 90)

# 통계학과이고 2학년 이상인 학생
filter(students, dept == "통계", year >= 2)

select() — 열 선택

필요한 열만 남깁니다.

# name과 score만 선택
select(students, name, score)

# score를 제외한 나머지
select(students, -score)

mutate() — 새 열 추가 / 기존 열 변환

기존 데이터를 바탕으로 새로운 열을 만듭니다.

mutate(students,
  grade = case_when(
    score >= 90 ~ "A",
    score >= 80 ~ "B",
    TRUE        ~ "C"
  ),
  score_scaled = score / 100
)

summarise() — 요약 통계

그룹별 또는 전체 요약 통계를 계산합니다.

# 전체 평균 점수
summarise(students, mean_score = mean(score))

# 학과별 평균 점수와 인원 수
students |>
  group_by(dept) |>
  summarise(
    mean_score = mean(score),
    n = n()
  )

arrange() — 정렬

# 점수 내림차순 정렬
arrange(students, desc(score))

# 학과별 오름차순, 같은 학과 안에서 점수 내림차순
arrange(students, dept, desc(score))

파이프 연산자로 연결하기

각 함수를 개별적으로 사용해도 되지만, 파이프(|>)로 연결하면 훨씬 읽기 쉬워집니다.

# 통계학과 학생을 점수 내림차순으로 정렬해 이름과 점수만 출력
students |>
  filter(dept == "통계") |>
  arrange(desc(score)) |>
  select(name, score)

Shiny 서버 코드에서도 이 패턴을 자주 사용합니다.

server <- function(input, output, session) {
  output$table <- renderTable({
    students |>
      filter(dept == input$dept_select) |>
      arrange(desc(score))
  })
}

tidyr 핵심 함수

tidyr은 데이터의 형태를 바꾸는 데 사용합니다.

pivot_longer() — 넓은 형태를 긴 형태로

scores_wide <- tibble(
  name = c("Alice", "Bob"),
  math = c(85, 90),
  english = c(78, 88),
  science = c(92, 75)
)

# 과목을 하나의 열로 모읍니다
scores_long <- pivot_longer(
  scores_wide,
  cols = c(math, english, science),
  names_to = "subject",
  values_to = "score"
)

결과는 아래와 같습니다.

# A tibble: 6 × 3
  name  subject  score
  <chr> <chr>    <dbl>
1 Alice math        85
2 Alice english     78
3 Alice science     92
4 Bob   math        90
5 Bob   english     88
6 Bob   science     75

긴 형태는 ggplot2로 그래프를 그릴 때 훨씬 편리합니다.

pivot_wider() — 긴 형태를 넓은 형태로

# 반대 방향으로 변환
pivot_wider(scores_long,
  names_from = subject,
  values_from = score
)

Shiny에서의 활용 예시

사용자가 학과를 선택하면 해당 학과 학생의 요약 통계를 보여주는 서버 로직 예시입니다.

server <- function(input, output, session) {
  output$summary <- renderTable({
    students |>
      filter(dept == input$dept) |>
      summarise(
        인원 = n(),
        평균점수 = round(mean(score), 1),
        최고점수 = max(score),
        최저점수 = min(score)
      )
  })
}

데이터 파이프라인을 reactive()로 감싸면 여러 출력에서 재사용할 수 있습니다. 이 내용은 PART 03에서 자세히 다룹니다.