R로 데이터 다루기

R에서 dplyr을 이용해 데이터를 추출, 가공하는 방법을 알아봅니다


수강중

14. dplyr 함수들을 조합한 실전 데이터 다루기 2 - 1

라이브러리 불러오기

library(dplyr)
Attaching package: ‘dplyr’

The following objects are masked from ‘package:stats’:

    filter, lag

The following objects are masked from ‘package:base’:

    intersect, setdiff, setequal, union

판매 데이터를 불러온다.

sales <- read.csv('sales.csv', stringsAsFactors = F,
                  fileEncoding = 'UTF-8')

변수명 한글에서 영문으로 변경

colnames(sales) <- c('city', 'district', 'gender', 'sales.nm', 'sales.cd', 'ymd', 'sales.num')

1번 문제

판매건수를 기준으로 WORST 10개를 출력해주세요.

arrange 함수, slice 사용

sales %>%
    arrange(sales.num) %>%
    slice(1:10)
   city       district gender sales.nm sales.cd ymd      sales.num
1  서울특별시 강남구   여     카페베타 12AA01   20140106 1        
2  서울특별시 강남구   남     카페베타 12AA01   20140106 1        
3  서울특별시 강남구   여     원조백반 100202   20140121 1        
4  서울특별시 강남구   남     원조백반 100202   20140121 1        
5  서울특별시 강남구   여     전주비빔 100203   20140126 1        
6  서울특별시 강남구   남     전주비빔 100203   20140126 1        
7  서울특별시 강남구   남     원조한식 100201   20140225 1        
8  서울특별시 강남구   여     카페베타 12AA01   20140302 1        
9  서울특별시 강남구   남     카페베타 12AA01   20140302 1        
10 서울특별시 강남구   남     키즈랜드 100101   20140307 1        

2번 문제

남자 중 판매건수를 기준으로 BEST 10개를 추출해보세요.

filter, arrange(desc) 사용

10개 이후에도 동률이 많아서 잘린 것을 알 수 있다. 동률이 있을 때는 데이터 순으로 출력이 된다.

sales %>%
    filter(gender == '남') %>%
    arrange(desc(sales.num)) %>%
    slice(1:10)
   city       district gender sales.nm sales.cd ymd      sales.num
1  서울특별시 강남구   남     스탑버스 12AA02   20140215 500      
2  서울특별시 강남구   남     베타문구 110002   20140411 500      
3  서울특별시 강남구   남     스탑버스 12AA02   20140411 500      
4  서울특별시 강남구   남     원조백반 100202   20140715 500      
5  서울특별시 강남구   남     원조백반 100202   20140730 500      
6  서울특별시 강남구   남     키즈랜드 100101   20141003 500      
7  서울특별시 강남구   남     @        @        20141202 500      
8  서울특별시 강동구   남     전주비빔 100203   20140221 500      
9  서울특별시 강동구   남     카페베타 12AA01   20140303 500      
10 서울특별시 강동구   남     베타문구 110002   20140308 500      

3번 문제

여자 & 강남구에서 판매건수를 기준으로 BEST 10개를 추출해보세요.

sales %>%
    filter(gender == '여' & district == '강남구') %>%
    arrange(desc(sales.num)) %>%
    slice(1:10)
   city       district gender sales.nm sales.cd ymd      sales.num
1  서울특별시 강남구   여     원조한식 100201   20140116 500      
2  서울특별시 강남구   여     스탑버스 12AA02   20140215 500      
3  서울특별시 강남구   여     스탑버스 12AA02   20140411 500      
4  서울특별시 강남구   여     원조백반 100202   20140715 500      
5  서울특별시 강남구   여     키즈랜드 100101   20141003 500      
6  서울특별시 강남구   여     원조한식 100201   20141202 500      
7  서울특별시 강남구   여     원조한식 100201   20140106 499      
8  서울특별시 강남구   여     원조백반 100202   20140126 499      
9  서울특별시 강남구   여     스탑버스 12AA02   20140210 499      
10 서울특별시 강남구   여     @        @        20140824 499      

4번 문제

여자 중에서 지역구별로 가장 많이 판매되는 업종 3개를 추출하세요.

filter, group_by, arrange 사용

판매 건수가 아니라 지역구별로 업종별을 구해야하기 때문에 group_by에 업종명이 들어가야한다. 지역구별로 업종이 나오고 그 업종에 대한 판매건수가 나와야지, 그 판매건수를 정렬했을 때, 업종 3개를 추출할 수 있다.

sales %>%
 filter(gender == '여') %>%
 group_by(district, sales.nm)
       city       district gender sales.nm sales.cd ymd      sales.num
1      서울특별시 강남구   여     키즈랜드 100101   20140101 309      
2      서울특별시 강남구   여     키즈랜드 100101   20140101 365      
3      서울특별시 강남구   여     스탑버스 12AA02   20140101 413      
4      서울특별시 강남구   여     레스탑   110001   20140101 287      

summarise(sum)

판매 합을 구한다. Na.rm=T로 결측치는 생략한다.

sales %>%
 filter(gender == '여') %>%
 group_by(district, sales.nm) %>%
 summarise(sum.sales.num = sum(sales.num, na.rm =T))
    district sales.nm sum.sales.num
1   강남구   @        116472       
2   강남구   레스탑   131487       
3   강남구   베타문구 132954       
4   강남구   스탑버스 131764       

arrange, slice, arrange

group_by로 지역구별로, 업종별로 정렬하고 slice로 3개씩 자른다.

sales %>%
 filter(gender == '여') %>%
 group_by(district, sales.nm) %>%
 summarise(sum.sales.num = sum(sales.num, na.rm =T)) %>%
 arrange(desc(sum.sales.num)) %>%
 slice(1:3)
    district sales.nm sum.sales.num
1   강남구   키즈랜드 141205       
2   강남구   원조백반 137990       
3   강남구   전주비빔 135366       
4   강동구   전주비빔 142596       

결과 확인

판매건수를 추출하는게 아니라 업종을 추출하는게 목적이다. group_by를 할 때 최종 목적이 구만 나오는게 아니라 업종도 같이 나와야한다. 업체명을 group_by에 안 넘겨주면 구만 3개가 나오게 된다.

4-2번 문제

여자 중에서 지역구별로 가장 많이 판매되는 업종 3개를 추출하고, 구별로 판매건수 합의 평균을 구하세요.

group_by, summarise

가장 많이 판매되는 업종 3개는 위의 코드를 사용한다. 그 결과에서 다시 group_by를 하여 구별로 계산하기 위해 district(구)를 넘겨주고 summarise를 적용한다.

판매 건수의 합에 대한 3개 업체의 평균 값을 추출해준다.

sales %>%
    filter(gender == '여') %>%
    group_by(district, sales.nm) %>%
    summarise(sum.sales.num = sum(sales.num, na.rm =T)) %>%
    arrange(desc(sum.sales.num)) %>%
    slice(1:3) %>%
    group_by(district) %>%
    summarise(mean.sales.num = mean(sum.sales.num, na.rm = T))
   district mean.sales.num
1  강남구   138187.0      
2  강동구   139317.0      
3  강북구   137130.3      
4  강서구   139120.7      
5  관악구   139837.3      
6  광진구   137487.7      
7  구로구   136165.7      
8  금천구   139700.3      
9  노원구   135992.7      
10 도봉구   135558.0      
11 동대문구 137137.0      
12 동작구   136020.0      
13 마포구   141338.7      
14 서대문구 134291.3      
15 서초구   137335.3      
16 성동구   136607.0      
17 성북구   136744.0      
18 송파구   135289.7      
19 양천구   138841.7      
20 영등포구 140280.7      
21 용산구   135325.7      
22 은평구   136936.0      
23 종로구   140209.3      
24 중구     140679.7      
25 중랑구   137301.0      

5번 문제

강남구에서 판매건수를 기준으로 BEST 50개를 출력하는데, 순위도 매겨주세요.

rank 설명 순위 매기는 법은 rank 함수를 사용하는데 이전 강의에서 다뤘으니 모르면 확인해라.

filter, arrange, slice

강남구만 filter를 하고 best니깐 arrange를 사용한다. 그리고 50개를 자른다.

sales %>%
    filter(district == '강남구') %>%
    arrange(desc(sales.num)) %>%
    slice(1:50)
   city       district gender sales.nm sales.cd ymd      sales.num
1  서울특별시 강남구   여     원조한식 100201   20140116 500      
2  서울특별시 강남구   여     스탑버스 12AA02   20140215 500      
3  서울특별시 강남구   남     스탑버스 12AA02   20140215 500      
4  서울특별시 강남구   NA     베타문구 110002   20140411 500      

mutate, rank

이제 50개를 잘랐으니 순위를 매기면 된다. mutate 한뒤에 rank 를 하여 순위를 추가한다. Ties.method=min으로 하여 동률이 났을 때는 둘다 최소값으로 나오게 한다. 1등이 두개 있으면 둘다 1등으로 해놓는다. 그 다음에 작은 것 부터 높은 순으로 순위가 매겨지는데 우리는 높은 것에서 부터 낮은 순으로 매겨지기때문에 앞에 -를 붙여준다.

sales %>%
    filter(district == '강남구') %>%
    arrange(desc(sales.num)) %>%
    slice(1:50) %>%
    mutate(rank = rank(-sales.num, ties.method = 'min'))
   city       district gender sales.nm sales.cd ymd      sales.num rank
1  서울특별시 강남구   여     원조한식 100201   20140116 500        1  
2  서울특별시 강남구   여     스탑버스 12AA02   20140215 500        1  
3  서울특별시 강남구   남     스탑버스 12AA02   20140215 500        1  
4  서울특별시 강남구   NA     베타문구 110002   20140411 500        1