系列文章目录
实验数据
1. systation 数据集
systation.csv 中包含的是沈阳地铁站相关线路的经纬度数据,字段介绍如下表:
station | 站名 | line | 线路编号 |
line_id | 站编号 | gps_lon | 站处于的经度 |
gps_lat | 站处于的维度 |
2. SY-20150401 数据集
SY-20150401.csv 中提供的是一卡通刷卡数据,字段介绍如下表:
V1 | 卡编号 | V2 | 刷卡日期 |
V3 | 刷卡时间 | V4 | 刷卡站点 |
V5 | 刷卡类型 | V6 | 票价 |
V7 | 是否优惠 |
注:输入数据后将字段名,重命名为c(“card_id”,“date”,“time”,“station”,“vehicle”,“money”,“property”)
提示:以下是本篇文章正文内容
一、实验目的
在学习了R 的一些处理数据的方法后,建议学习下其他数据处理的第三方包,如之前介绍的data.table。
推荐学习包:dplyr 、tidyr 和lubridate
二、实验内容
题目1 数据处理【只用 SY-20150401.csv】
统计每 5 分钟,各站点的进出站流量(说明:00:00:01 在第一个 5 分钟内,00:10:13 在第三个 5 分钟内),由于一天可能多次乘坐地铁,根据卡号和进站时间,查询最近出站的时间,作为本次出站时间。
参考函数 lubridate::hms,lubridate:: period_to_seconds。
处理的最终结果:dataframe(名称 trade.metro.in.out )。
card.id | 卡id | time.in | 进站时间 |
line.in | 进站路线 | station.in | 进站站点 |
M5.in | 第几个5分钟进站 | time.out | 出站时间 |
line.out | 出站线路 | station.out | 出站站点 |
money | 票价 | M5.out | 第几个5分钟出站 |
duration | 乘坐时间(单位:秒) |
提交的表格按照card.id 排序。Notebook 中展示输出结果为head(trade.metro.in.out,10),并输出本地文件shmetro_line_in_out.csv。
题目2 统计进站与出站之间的流量
通过题目 1 中的 dataframe(trade.metro.in.out)进行统计,统计进站与出站之间的流量;然后选取流量最大的前 10 个站点,在 Notebook 中查看前 6 条。
三、实现过程与实验结果
题目1 数据处理【只用 SY-20150401.csv】
统计每 5 分钟,各站点的进出站流量(说明:00:00:01 在第一个 5 分钟内,00:10:13在第三个5分钟内),由于一天可能多次乘坐地铁,根据卡号和进站时间,查询最近出站的时间,作为本次出站时间。
提交的表格按照card.id排序。Notebook中展示输出结果为head(trade.metro.in.out,10)并输出本地文件shmetro_line_in_out.csv。
处理的最终结果:dataframe(名称 trade.metro.in.out)
card.id | 卡id | time.in | 进站时间 |
line.in | 进站路线 | station.in | 进站站点 |
M5.in | 第几个5分钟进站 | time.out | 出站时间 |
line.out | 出站线路 | station.out | 出站站点 |
money | 票价 | M5.out | 第几个5分钟出站 |
duration | 乘坐时间(单位:秒) |
# 读取数据
df <- read.csv("R\\data\\ex5\\SY-20150401.csv")
# 数据维度
dim(df)
## [1] 1048575 7
# 查看数据
head(df)
## X2002062859 X2015.4.1 X16.41.37 X2号线工业展览馆站 地铁 X0 非优惠
## 1 3103531702 2015/4/1 9:23:11 2号线金融中心站 地铁 4 非优惠
## 2 3001771678 2015/4/1 16:41:23 1号线十三号街站 地铁 0 非优惠
## 3 400679513 2015/4/1 16:47:09 1号线迎宾路站 地铁 0 非优惠
## 4 3102186320 2015/4/1 18:58:08 1号线七号街站 地铁 4 非优惠
## 5 740476054 2015/4/1 11:36:33 2号线市府广场站 地铁 0 非优惠
## 6 2301712030 2015/4/1 18:04:23 1号线开发大道站 地铁 0 非优惠
# 字段重命名
colnames(df)
## [1] "X2002062859" "X2015.4.1" "X16.41.37"
## [4] "X2号线工业展览馆站" "地铁" "X0"
## [7] "非优惠"
colnames(df) <- c('card.id','date','time','station','vehicle','money','property')
colnames(df)
## [1] "card.id" "date" "time" "station" "vehicle" "money" "property"
# 取出刷卡类型为地铁的数据
trade.metro <- df[df$vehicle == "地铁",]
# 刷卡站点(2号线金融中心站)按'号线'分割分成2个字段line(2)和station(金融中心站)
# install.packages("tidyr")
library(tidyr)
trade.metro <- separate(trade.metro, station, c('line', 'station'), sep = '号线')
head(trade.metro)
## card.id date time line station vehicle money property
## 1 3103531702 2015/4/1 9:23:11 2 金融中心站 地铁 4 非优惠
## 2 3001771678 2015/4/1 16:41:23 1 十三号街站 地铁 0 非优惠
## 3 400679513 2015/4/1 16:47:09 1 迎宾路站 地铁 0 非优惠
## 4 3102186320 2015/4/1 18:58:08 1 七号街站 地铁 4 非优惠
## 5 740476054 2015/4/1 11:36:33 2 市府广场站 地铁 0 非优惠
## 6 2301712030 2015/4/1 18:04:23 1 开发大道站 地铁 0 非优惠
# 专门用于数据处理的包
# mutate() 创建新变量 mutate(要修改的数据框的名称 ,将创建的新变量的名称=将分配给新变量的值)
# install.packages('dplyr')
library(dplyr)
# 日期时间处理
# period_to_seconds 以秒为单位转换时间戳;hms(秒,分,时,日) 用于创建一个hms类型的对象
# install.packages('lubridate')
library(lubridate)
# %>% 管道操作 将一个值或表达式的结果转发到下一个函数调用/表达式中
# 按5分钟统计时间
trade.metro <- trade.metro %>% mutate(M5 = ceiling(period_to_seconds(hms(time)) / 300))
head(trade.metro)
## card.id date time line station vehicle money property M5
## 1 3103531702 2015/4/1 9:23:11 2 金融中心站 地铁 4 非优惠 113
## 2 3001771678 2015/4/1 16:41:23 1 十三号街站 地铁 0 非优惠 201
## 3 400679513 2015/4/1 16:47:09 1 迎宾路站 地铁 0 非优惠 202
## 4 3102186320 2015/4/1 18:58:08 1 七号街站 地铁 4 非优惠 228
## 5 740476054 2015/4/1 11:36:33 2 市府广场站 地铁 0 非优惠 140
## 6 2301712030 2015/4/1 18:04:23 1 开发大道站 地铁 0 非优惠 217
# 进站数据统计 进站时money=0
trade.metro.in <- trade.metro %>% filter(money == 0) %>%
select(
card.id,
"time.in" = time,
"line.in" = line,
"station.in" = station,
"M5.in" = M5
)
head(trade.metro.in)
## card.id time.in line.in station.in M5.in
## 1 3001771678 16:41:23 1 十三号街站 201
## 2 400679513 16:47:09 1 迎宾路站 202
## 3 740476054 11:36:33 2 市府广场站 140
## 4 2301712030 18:04:23 1 开发大道站 217
## 5 2302067279 11:30:22 2 中医药大学站 139
## 6 2202626963 18:59:08 1 *大街站 228
# 出站数据统计 进站时money>0
trade.metro.out <- trade.metro %>% filter(money > 0) %>%
select(
card.id,
"time.out" = time,
"line.out" = line,
"station.out" = station,
"M5.out" = M5
)
head(trade.metro.out)
## card.id time.out line.out station.out M5.out
## 1 3103531702 9:23:11 2 金融中心站 113
## 2 3102186320 18:58:08 1 七号街站 228
## 3 2802877677 18:58:49 1 铁西广场站 228
## 4 2101871077 19:00:57 1 张士站 229
## 5 2503379038 11:32:21 2 市府广场站 139
## 6 2402957072 9:22:36 2 金融中心站 113
# 将进站数据和出站数据合并 计算乘车时长 取出乘车时长大于0的数据
trade.metro.in.out <-
merge(trade.metro.in, trade.metro.out, by = "card.id") %>%
mutate(duration = (period_to_seconds(hms(time.out)) - period_to_seconds(hms(time.in)))) %>%
filter(duration > 0)
head(trade.metro.in.out)
## card.id time.in line.in station.in M5.in time.out line.out
## 1 6032 14:17:33 2 航空航天大学站 172 15:34:24 2
## 2 56702 8:45:15 1 开发大道站 106 14:09:12 1
## 3 68597 17:26:19 2 市图书馆站 210 17:30:53 2
## 4 71082 10:30:22 2 金融中心站 127 10:59:12 2
## 5 71082 9:37:14 2 新乐遗址站 116 10:59:12 2
## 6 71082 9:37:14 2 新乐遗址站 116 9:59:40 2
## station.out M5.out duration
## 1 航空航天大学站 187 4611
## 2 开发大道站 170 19437
## 3 五里河站 211 274
## 4 新乐遗址站 132 1730
## 5 新乐遗址站 132 4918
## 6 金融中心站 120 1346
# 根据卡号和进站时间 查询最近出站的时间 作为本次出站时间
# install.packages("data.table")
library(data.table)
trade.metro.in.out <- data.table(trade.metro.in.out)
trade.metro.in.out[, duration_min := min(duration), by=list(card.id, M5.in)]
trade.metro.in.out <- trade.metro.in.out %>% filter(duration==duration_min) %>% select(-duration_min)
head(trade.metro.in.out)
## card.id time.in line.in station.in M5.in time.out line.out
## 1: 6032 14:17:33 2 航空航天大学站 172 15:34:24 2
## 2: 56702 8:45:15 1 开发大道站 106 14:09:12 1
## 3: 68597 17:26:19 2 市图书馆站 210 17:30:53 2
## 4: 71082 10:30:22 2 金融中心站 127 10:59:12 2
## 5: 71082 9:37:14 2 新乐遗址站 116 9:59:40 2
## 6: 72845 8:46:10 1 十三号街站 106 19:43:11 1
## station.out M5.out duration
## 1: 航空航天大学站 187 4611
## 2: 开发大道站 170 19437
## 3: 五里河站 211 274
## 4: 新乐遗址站 132 1730
## 5: 金融中心站 120 1346
## 6: 十三号街站 237 39421
# 按照card.id来排序 展示前10条
trade.metro.in.out <- trade.metro.in.out[order(trade.metro.in.out$card.id),]
head(trade.metro.in.out,10)
## card.id time.in line.in station.in M5.in time.out line.out
## 1: 6032 14:17:33 2 航空航天大学站 172 15:34:24 2
## 2: 56702 8:45:15 1 开发大道站 106 14:09:12 1
## 3: 68597 17:26:19 2 市图书馆站 210 17:30:53 2
## 4: 71082 10:30:22 2 金融中心站 127 10:59:12 2
## 5: 71082 9:37:14 2 新乐遗址站 116 9:59:40 2
## 6: 72845 8:46:10 1 十三号街站 106 19:43:11 1
## 7: 79796 7:53:16 1 怀远门站 95 22:19:52 1
## 8: 88873 14:01:19 1 铁西广场站 169 14:17:02 1
## 9: 90573 7:47:43 1 迎宾路站 94 8:21:41 1
## 10: 95504 5:55:08 1 南市场站 72 6:29:52 1
## station.out M5.out duration
## 1: 航空航天大学站 187 4611
## 2: 开发大道站 170 19437
## 3: 五里河站 211 274
## 4: 新乐遗址站 132 1730
## 5: 金融中心站 120 1346
## 6: 十三号街站 237 39421
## 7: 怀远门站 268 51996
## 8: 于洪广场站 172 943
## 9: 滂江街站 101 2038
## 10: 七号街站 78 2084
# 输出本地文件
write.csv(trade.metro.in.out,"shmetro_line_in_out.csv",row.names = F)
题目2 统计进站与出站之间的流量
统计进站与出站之间的流量:通过题目1的dataframe(trade.metro.in.out)进行统计,统计进站与出站之间的流量;然后选取流量最大的前 10 个站点,在 Notebook 中查看前 6 条。
# 按station.in,station.out分组
trade.metro.in.out <- data.table(trade.metro.in.out)
a <- trade.metro.in.out[, .(passenger.flow = .N), keyby = .(station.in, station.out)]
head(a, 10)
## station.in station.out passenger.flow
## 1: 七号街站 七号街站 4470
## 2: 七号街站 三台子站 54
## 3: 七号街站 世纪大厦站 18
## 4: 七号街站 东中街站 165
## 5: 七号街站 中医药大学站 92
## 6: 七号街站 *大街站 224
## 7: 七号街站 中街站 147
## 8: 七号街站 于洪广场站 442
## 9: 七号街站 云峰北街站 226
## 10: 七号街站 五里河站 46
# 按照进出站的流量排序取出前10个
a <- a[order(a$passenger.flow, decreasing = TRUE), ]
b <- a[1:10, ]
# 展示前6个
head(b, 6)
## station.in station.out passenger.flow
## 1: 十三号街站 十三号街站 6345
## 2: 七号街站 七号街站 4470
## 3: 航空航天大学站 航空航天大学站 3035
## 4: 全运路站 全运路站 2717
## 5: 营盘街站 营盘街站 2345
## 6: 滂江街站 滂江街站 1996