본문 바로가기
데이터분석/R

[R 데이터분석 with 샤이니] 교통 카드 데이터 분석 사례 04 - 종합 분석

by 버섯도리 2022. 8. 6.

> ## 8 종합 분석


> # Step 1 : 버스노선 네트워크 만들기

> ## 화성시 대중교통 이동 네트워크
> # 데이터 불러오기
> setwd(dirname(rstudioapi::getSourceEditorContext()$path))
> load("./01_save/04_002_trip_chain.rdata")
> load("./01_save/04_003_grid_chain.rdata")
> load("./01_save/04_001_sta_pnt.rdata")
> load("./01_save/01_002_fishnet.rdata")
> load("./01_save/01_001_admin.rdata")
> ## 집계구 간 이동만 남기기(집계구 내 이동 지우기)
> library(stplanr)
> od_intra <- filter(grid_chain, id.x != id.y)
> # 그리드 간(intra) 이동별 총이용객수, 환승횟수 집계하기
> od_intra2 <- od_intra %>%
+   group_by(id.x, id.y) %>%
+   summarise_each(funs(sum)) %>%
+   dplyr::select(id.x, id.y, 총이용객수, 환승횟수)
> # 평균 환승횟수 계산
> od_intra2$평균환승 <- round((od_intra2$환승횟수 / od_intra2$총이용객수), 1)
> # 컬럼 이름 정리하기
> colnames(od_intra2) <- c("id.x", "id.y", "총이용객수", "환승횟수", "평균환승")
> od_line <- od2line(od_intra2, as(fishnet, "sf"))
Creating centroids representing desire line start and end points.
> save(od_line, file = "./01_save/08_001_od_line.rdata")

> ## OD라인 시각화
> # 이용자수 20건 이상 필터링
> library(dplyr)
> od_line <- od_line[od_line$총이용객수 %in% 20:3000, ]
> library(tmap)
> qtm("Hwaseong")
> qtm("Hwaseong") +
+   tm_basemap("OpenStreetMap") +
+   qtm(od_line, lines.lwd = "총이용객수", lines.col = "red")
Legend for line widths not available in view mode.
Warning message:
qtm called without shape objects cannot be stacked 


> ## 네트워크 속성 변환 (Spatial_data_frame => Spatial_Network)
> library(stplanr)
> od_line_sln <- SpatialLinesNetwork(od_line)
> library(igraph)
> E(od_line_sln@g)$weight <- od_line$총이용객수
> edge_attr(od_line_sln@g)$weight
  [1]   24   48   32   48   24   28   34   48   28   23  151   40   20  132   21  148   56   25   25   45   28   33   67
 [24]   40  124   60   48  156  112   24   21   42   27   51   21   30  156   24   36   48   88   69 2565  423 1524   60
 [47]  282  150  135  756  522  186  456   30  180   30   75  264  384   87   36   39  180   27  792   48   36   27   48
...
[714]   28   30   92   36   25  196   61   35
> l_out <- cbind(od_line_sln@g$x, od_line_sln@g$y)
> save(l_out, file = "./01_save/08_002_l_out.rdata")
> # 플로팅
> plot(admin, lwd = 1, border = "grey", main = "화성시 대중교통 이동 네트워크",
+      xlim = c(126.93, 127.16), ylim = c(37.1, 37.3))
plot.igraph(od_line_sln@g,
+             vertex.label = V(od_line_sln@g), vertex.label.color = "black", vertex.label.cex = .8,
+             vertex.size = 0.03*igraph::degree(od_line_sln@g),
+             vertex.color = adjustcolor("blue", alpha.f = .4),
+             edge.width = edge_attr(od_line_sln@g)$weight/1000,
+             edge.color = "orange",
+             edge.curved = 0.3,
+             layout = l_out,
+             rescale = F, add = T
+ )

> ## Edge의 역가중치(inverse weight)를 표준화 하기 (***)
> edge_attr(od_line_sln@g)$weight <- (max(edge_attr(od_line_sln@g)$weight) - edge_attr(od_line_sln@g)$weight) / (max(edge_attr(od_line_sln@g)$weight) - min(edge_attr(od_line_sln@g)$weight))
plot(density(edge_attr(od_line_sln@g)$weight), main="")

>

> # Step 2 : 최적 노선 도출 및 시각화

> ## 최적 노선 시각화

> #---#
> # 향남(54) - 병점역(19) - 삼성 화성캠퍼스(2) - 동탄 이지더원 아파트(21)
> #---#
> # 향남(54) - 병점역(19)
> path1 <- shortest_paths(od_line_sln@g, from = "54", to = "19", output = "both")
> unlist(path1$epath)
[1] 695 679
> # 병점역(19) - 삼성 화성캠퍼스(2)
> path2 <- shortest_paths(od_line_sln@g, from = "19", to = "2", output = "both")
> unlist(path2$epath)
[1] 480 481
> # 삼성 화성캠퍼스(2) - 동탄 이지더운 아파트(21)
> path3 <- shortest_paths(od_line_sln@g, from = "2", to = "21", output = "both")
> unlist(path3$epath)
[1]  39 572

> ecol <- rep(NA, ecount(od_line_sln@g))
> ecol[unlist(c(path1$epath, path2$epath, path3$epath))] <- "red"
> edge_attr(od_line_sln@g)$weight[unlist(c(path1$epath, path2$epath, path3$epath))] <- 1500

> #---#
> # 레이크빌(36) - 동탄 이지더원 아파트(21) - 삼성 화성캠퍼스(6) - 삼성 수원 디지털 본사(39)
> #---#
> # 레이크빌(36) - 동탄 이지더원 아파트(21)
> path1 <- shortest_paths(od_line_sln@g, from = "36", to = "21", output = "both")
> unlist(path1$epath)
[1] 625 249 250
> # 동탄 이지더원 아파트(21) - 삼성 화성캠퍼스(6)
> path2 <- shortest_paths(od_line_sln@g, from = "21", to = "6", output = "both")
> unlist(path2$epath)
[1] 296 159
> # 삼성 화성캠퍼스(6) - 삼성 수원 디지털 본사(39)
> path3 <- shortest_paths(od_line_sln@g, from = "6", to = "39", output = "both")
> unlist(path3$epath)
[1] 159 281

> ecol[unlist(c(path1$epath, path2$epath, path3$epath))] <- "blue"
> edge_attr(od_line_sln@g)$weight[unlist(c(path1$epath, path2$epath, path3$epath))] <- 1500

> # 향남(54) - 오산역(49)
> path1 <- shortest_paths(od_line_sln@g, from = "54", to = "49", output = "both")
> unlist(path1$epath)
[1] 668
> ecol[unlist(path1$epath)] <- "darkorange"
> edge_attr(od_line_sln@g)$weight[unlist(path1$epath)] <- 600

> # 동탄 이지더원 아파트(21) - 보정역(58)
> path1 <- shortest_paths(od_line_sln@g, from = "21", to = "58", output = "both")
> unlist(path1$epath)
[1] 568 404 403
> ecol[unlist(path1$epath)] <- "darkorchid1"
> edge_attr(od_line_sln@g)$weight[unlist(path1$epath)] <- 600

plot(admin, lwd = 1, border = "grey", main = "화성시 신규 버스노선",
+      xlim = c(126.93, 127.16), ylim = c(37.1, 37.3))
plot(od_line_sln@g, vertex.label = NA, vertex.size = 0.01,
+      edge.width = 4*edge_attr(od_line_sln@g)$weight/1000, edge.color = ecol,
+      edge.curved = 0.1, layout = l_out, rescale = F, add = T)

> # 향남(54)
> text(od_line_sln@g$x[54], od_line_sln@g$y[54], "향남", cex = 1.2, pos = 1)
> # 병점역(19)
> text(od_line_sln@g$x[19], od_line_sln@g$y[19], "병점역", cex = 1.2, pos = 2)
> # 삼성 화성캠퍼스(2)
> text(od_line_sln@g$x[2], od_line_sln@g$y[2], "삼성 화성캠", cex = 1.2, pos = 3)
> # 동탄 이지더원 아파트(21)
> text(od_line_sln@g$x[21], od_line_sln@g$y[21], "이지원A", cex = 1.2, pos = 4)
> # 레이크빌(36)
> text(od_line_sln@g$x[36], od_line_sln@g$y[36], "레이크빌A", cex = 1.2, pos = 4)
> # 삼성 화성캠퍼스(6)
> text(od_line_sln@g$x[6], od_line_sln@g$y[6], "삼성 화성캠", cex = 1.2, pos = 2)
> # 삼성 수원캠퍼스(39)
> text(od_line_sln@g$x[39], od_line_sln@g$y[39], "삼성 수원캠", cex = 1.2, pos = 2)
> # 오산역(49)
> text(od_line_sln@g$x[49], od_line_sln@g$y[49], "오산역", cex = 1.2, pos = 4)
> # 보정역(58)
> text(od_line_sln@g$x[58], od_line_sln@g$y[58], "보정역", cex = 1.2, pos = 4)

box(lty = "solid", col = "black")
legend(od_line_sln@g$x[43]+0.02, od_line_sln@g$y[43]+0.04,
+        legend = c("향남-이지더원A", "레이크빌A-삼성 수원캠", "향남-오산역", "보정역-이지더원A"),
+        col = c("red", "blue", "darkorange", "darkorchid1"), lty = 1, cex = .8)

 

 

 

 

 

 

출처 : 김철민, ⌜공공데이터로 배우는 R 데이터분석 with 샤이니⌟, 이지스퍼블리싱, 2022