07-1. 빠진 데이터를 찾아라! - 결측치 정제하기

결측치(Missing Value)란?

- 누락된 값, 비어 있는 값을 의미

 

결측치 찾기

1. 결측치 가진 데이터 프레임 만들기

df <- data.frame(sex=c("M","F",NA,"M","F"), score=c(5,4,3,4,NA))

2. 결측치 확인하기 - is.na() 사용하기 (결측치는 TRUE, 결측치가 아닌 값은 FALSE로 표시)

is.na(df)

is.na()를 사용해 결측치 확인

3. 데이터에 결측치가 몇 개 있는지 출력 - is.na()를 table()에 적용

table(is.na(df))

4. 결측치가 존재하는 변수 확인

 

 결측치 제거

1. 결측치 있는 행 제거하기 - '행'이므로 is.na()를 filter()에 적용

df %>% filter(is.na(score))

2. score의 값이 NA가 아닌 행들 출력

df %>% filter(!is.na(score))

3. 추출한 데이터로 데이터 프레임을 만들면 결측치가 없는 데이터가 생성됨

df_nomiss <- df %>% filter(!is.na(score))  #score 결측치 제거
mean(df_nomiss$score)  #score 평균 산출
sum(df_nomiss$score)  #score 합계 산출

결측치 없는 데이터

 

cf) na.omit() 을 이용하면 변수를 지정하지 않고 결측치가 있는 행을 한 번에 제거

df_nomiss2 <- na.omit(df)

na.omit()는 결측치가 하나라도 있으면 모두 제거하기 때문에 간편하게 쓸 수 있지만 분석에 필요한 데이터가 일부 손실된다는 단점이 있음. 따라서 filter()를 이용해 분석에 사용할 변수의 결측치만 제거하는 방식을 권함.

 

함수의 결측치 제외 기능 이용하기

** mean()과 같은 수치 연산 함수들은 결측치를 제외하고 연산하도록 설정하는 na.rm 파라미터를 지원한다. na.rm을 TRUE로 설정하면 결측치를 제외하고 함수를 적용하기 때문에 결측치를 제거하는 절차를 건너뛰고 곧바로 분석할 수 있다. 하지만 모든 함수가 na.rm을 지원하는 것이 아니기 때문에 filter()로 결측치를 제거한 후에 함수를 적용하는 순으로 작업해야 한다.

1. na.rm() 파라미터 사용

mean(df$score, na.rm=T)  #결측치를 제외하고 평균 산출
sum(df$score, na.rm=T)  #결측치를 제외하고 합계 산출

2. summarise()도 na.rm 적용 가능

exam<-read.csv("csv_exam.csv")
exam[c(3, 8, 15), "math"] <- NA

summarise()에 mean()과 sum(), median() 함수를 불러온 다음 na.rm을 사용해서 결측치를 제외하고 값을 구함.

exam %>% summarise(mean_math = mean(math, na.rm = T),
		sum_math = sum(math, na.rm = T),
        median_math = median(math, na.rm = T))

mean_math sum_math median_math
 55.23529      939          50

 

 

 결측치 대체하기

1. 앞에서 만든 exam 데이터에서 3, 8, 15행의 math는 결측치. 이 값들을 평균값으로 대체하기 위해 먼저 math의 평균값을 구해보자.

mean(exam$math, na.rm = T)

결측치 제외한 math 평균, 약 55

 

2. 결측치를 평균값으로 대체 - ifelse()를 이용해 NA값을 평균값으로 대체 (math가 NA면 55를 입력하고 그렇지 않으면 원래의 값을 그대로 둠)

exam$math <- ifelse(is.na(exam$math), 55, exam$math)
table(is.na(exam$math))

math의 결측치가 55로 수정됨

 

 

 

(출처; 쉽게 배우는 R 데이터 분석, 김영우)

 

dplyr 패키지에 있는 함수 알아보기

 

많이 사용하는 함수 종류

dplyr 패키지 설치하기

library(dplyr)

 

filter() - 조건에 맞는 데이터만 추출하기

<1> dplyr 패키지를 로드한 후 csv_exam.csv 파일을 데이터 프레임으로 만들어 출력하기

exam <- read.csv("csv_exam.csv")
exam

<2> dplyr 패키지의 filter 함수를 이용하여 1반 학생들의 데이터만 추출하기

exam %>% filter(class==1)

<3> 같은 형식으로 2반 학생들의 데이터만 추출하기

exam %>% filter(class=2)

<4> 변수가 '특정 값이 아닌 경우'에 해당하는 데이터 추출하기

exam %>% filter(class != 1)  #1반이 아닌 학생만 추출

 

 

select() - 필요한 변수만 추출하기

<1> select() 이용하여 수학 점수만 추출하기

exam %>% select(math)

<2> select() 이용하여 여러 변수 추출하기

exam %>% select(class, math, english)

<3> 특정 변수 제외하기

exam %>% select(-english)

 

 

arrange() - 순서대로 정렬하기

<1> 오름차순으로 정렬하기

english 변수의 값을 기준으로 오름차순으로 정렬됨

<2> 내림차순으로 정렬하기

english 변수의 값을 기준으로 내림차순으로 정렬됨
쉼표를 사용하여 여러 변수 한 번에 정렬 가능

 

 

mutate() - 파생변수 추가하기★

<1> 파생변수 추가하기

세 과목의 점수를 모두 더한 total이라는 파생 변수 추가

<2> 여러 파생변수 한 번에 추가하기

+

세 과목 점수를 더한 total 변수의 상위 5개

 

summarise() - 요약하기

** summarise 함수에는 연속형 변수만 들어갈 수 있다. (주로 group_by 함수와 같이 사용)

group_by() - 집단별로 나누기

** group_by 함수에는 범주형 변수만 들어갈 수 있다.

 

 

(출처; 쉽게 배우는 R 데이터 분석, 김영우)

<쉽게 배우는 R 데이터 분석 p.160>

문제 1. popadults 는 해당 지역의 성인 인구, poptotal은 전체 인구를 나타냅니다. midwest 데이터에 '전체 인구 대비 미성년 인구 백분율' 변수를 추가하세요.

total 이라는 새로운 변수 추가

 

문제 2. 미성년 인구 백분율이 가장 높은 상위 5개 country(지역)의 미성년 인구 백분율을 출력하시오.

문제 3. 다음과 같은 분류표의 기준에 따라 미성년 비율 등급 변수를 추가하고, 각 등급에 몇 개의 지역이 있는지 알아보세요.
library(ggplot2)
data <- data %>% mutate(level = ifelse(data$total >= 40, "large",
					ifelse(data$county > 30, "middle", "small")))
table(data$level)
qplot(data$level)

large middle small
   32    396     9

 

문제 4. popasian은 해당 지역의 아시아인 인구를 나타냅니다. '전체 인구 대비 아시아인 인구 백분율' 변수를 추가하고 하위 10개 지역의 state(주), county(지역), 아시아인 인구 백분율을 출력하세요.
data <- midwest %>%
	mutate(tot_asian = (popasian/poptotal)*100) %>%
    arrange(tot_asian) %>%
    select(state, county, tot_asian) %>%
    tail(10)
data

 

(출처; 쉽게 배우는 R 데이터 분석, 김영우)

EDA 중 '데이터 모양 확인하기' 파트

 

<1> 데이터 파악하기

- 데이터가 주어졌을 때 가장 먼저 하는 일은 데이터의 전반적인 구조를 파악하는 것. 어떤 변수들이 있는지, 몇 행으로 구성되어 있는지 전반적인 구조를 살펴본다.

 

데이터를 파악할 때 사용하는 기본 함수들

1.  head( ) - 데이터 앞부분 확인하기

- 데이터의 앞부분을 출력하는 기능. 괄호 안에 데이터 프레임 이름을 입력하고 실행하면 앞에서부터 여섯 번째 행까지 출력된다.   ex. head(exam)

- 여섯 번째 행보다 더 아래 행까지 출력하고 싶으면 데이터 프레임 이름 뒤에 쉼표를 쓰고 숫자를 입력하면 입력한 행까지의 데이터를 출력할 수 있다.     ex. head(exam, 10) #앞에서부터 10행까지 출력

 

2. tail( ) - 데이터 뒷부분 확인하기

- 데이터의 뒷부분을 출력하는 기능. 괄호 안에 데이터 프레임 이름을 입력하고 실행하면 뒤에서부터 여섯 행을 출력된다. ex. tail(exam)

- head함수와 마찬가지로 숫자를 입력하면 원하는 만큼의 행을 출력할 수 있다. ex. tail(exam, 10) #뒤에서부터 10행까지 출력

 

3. View( ) - 뷰어 창에서 데이터 확인하기 (*V는 대문자로 입력)

- 엑셀과 유사하게 생긴 '뷰어 창'에 원자료를 직접 보여 주는 기능. 원자료를 눈으로 직접 확인해 보고 싶을 때 사용한다.

 

4.  dim( ) - 데이터가 몇 행, 몇 열로 구성되어 있는지 알아보기

- 데이터 프레임이 몇 행, 몇 열로 구성되어 있는지 알아볼 때 사용. 출력된 2개 숫자 중에서 앞의 숫자는 '행', 뒤의 숫자는 '열'의 개수를 나타낸다.

- [1] 20  5 이렇게 출력되었다면 >> 이 데이터는 20행, 5열로 구성되어 있다는 것을 의미

 

5. str( ) - 속성 파악하기

- 데이터에 들어 있는 변수들의 속성을 보여준다. 모든 변수의 속성을 한 눈에 파악하고 싶을 때 사용

str(exam)  # 데이터 속성 확인

## 'data.frame' :    20 obs. of 5 variables:  # 데이터의 속성과 몇 개의 관측치와 변수로 구성되어 있는지 표시됨
## $ id      :  int  1 2 3 4 5 6 7 8 9 10 . . .  
## $ class   :  int  1 1 1 1 2 2 2 2 3 3 . . .
## $ math    :  int  50 60 45 30 25 50 80 90 20 50 . . .
## $ english :  int  98 97 86 98 80 89 90 78 98 98 . . .
## $ science :  int  50 60 76 38 60 45 97 85 50 70 . . .

- 위의 출력 결과 예시를 보면 exam 데이터가 데이터 프레임이고, 20개의 관측치와 5개의 변수로 구성되어 있음을 알 수 있다.

 

6. summary( ) - 요약 통계랑 산출하기

- '평균'처럼 변수의 값을 요약한 '요약 통계량'을 산출. ex. 중앙값과 평균 등

- 요약 통계량을 보면 변수의 특성을 파악하는데 도움이 됨

- 수치에 관해 나타내는 것이므로 '연속형 데이터'에만 의미 있음.

summary( )를 실행해 출력되는 요약 통계량들

 

(어떤 데이터를 분석하든, 가장 먼저 이러한 함수들을 활용해 전반적인 특징을 파악하는 작업을 해야함)

 

<2> 변수명 바꾸기

- 데이터의 전반적인 특징을 파악하고 나면 본격적으로 분석하기 전에 변수명을 수정하는 작업을 해야 한다. 변수명이 기억하기 어려운 문자로 되어 있으면 쉬운 단어로 변경하는 게 좋다.

ex.  분석하고자 하는 데이터에서 성별을 s_12 이런식으로 저장해두었다면 분석하기 전 sex로 바꿔놓는 것이 이해하기 쉽고 헷갈리지 않게 작업할 수 있다. 

 

*dplyr 패키지의 rename( )을 이용해 변수명 바꾸기

# 실습에 활용할 데이터 프레임 생성

df_raw <- data.frame(var1 = c(1, 2, 1), var2 = c(2, 3, 2))

df_raw

##    var1 var2
## 1     1    2
## 2     2    3
## 3     1    2
# rename( )을 이용하기 위해 dplyr 패키지 설치 후 로드 (dplyr은 데이터 조작 패키지)

install.packages("dplyr")  # dplyr 설치
library(dplyr)             # dplyr 로드

 

》 데이터 프레임 복사본 만들기 (중요)

- 변수명을 바꾸기 전에 원본을 보유하기 위해 데이터 프레임 복사본을 만든다. 새로운 변수명 df_new에 df_raw를 할당하는 형태로 코드 작성

df_new <- df_raw  # 복사본 생성

 

》 변수명 바꾸기

- rename(데이터 프레임명, 새 변수명 = 기존 변수명)  // 괄호 안의 것들이 순서가 바뀌면 실행되지 않음.

df_new <- rename(df_new, v2 = var2)  # var2를 v2로 수정
df_new

##    var1   v2
## 1     1    2
## 2     2    3
## 3     1    2

 

 

3. 파생변수 만들기

- 데이터에 들어 있는 변수만 이용해 분석할 수도 있지만, 변수를 조합하거나 함수를 적용해 새 변수를 만들어 분석할 수 있음. 기존의 변수를 변형해 만든 변수를 '파생변수(Derived Variable)'라고 한다. 

ex. 학생들의 이름, 영어 점수, 수학 점수로 이루어진 데이터에 각 학생별 영어 점수와 수학 점수의 '평균' 변수를 새로 만들 수 있음

 

** 변수를 조합해 파생변수 만들기

# 실습에 활용할 2개의 변수로 구성된 데이터 프레임 생성

df <- data.frame(var1 = c(4, 3, 8), var2 = c(2, 6, 1))

df
##    var1 var2
## 1     4    2
## 2     3    6
## 3     8    1
df$var_sum <- df$var1 + df$var2  # var_sum 이라는 파생변수 생성
df

##    var1 var2 var_sum
## 1     4    2       6
## 2     3    6       9
## 3     8    1       9
df$var_mean <- (df$var1 + df$var2)/2  # var_mean 이라는 파생변수 생성
df

##    var1 var2 var_sum var_mean
## 1     4    2       6      3.0
## 2     3    6       9      4.5
## 3     8    1       9      4.5

 

 

 

 

(출처; 쉽게 배우는 R 데이터 분석, 김영우)

+ Recent posts