B 答疑

菜鸟常犯错误和常见问题

读取数据文件(read.table())时,显示无法打开连接(Error in file(file, "rt") : cannot open the connection

很有可能是路径的名称写错了。路径的名称应该是个字符串。相邻两级文件夹之间要用\\或/分开,不能有汉字或特殊字符。最好不要有空格。如果有空格,要用\进行转义。下面是一些路径示例。

read.csv(c:/r4r/co2.csv) # 错误
# 文件完整路径必须是个字符串,放在一对儿单引号或双引号里。
# 不要用中文里的引号。

read.csv('c:\r4r\\co2.csv') # 错误  
# c:后面跟两个反斜线或一个斜线。
# 相邻两级文件夹之间必须是两个反斜线\\或一个斜线/。

read.csv('c:/r4r/co2.scv') # 错误
# 文件名不要写错,应为co2.csv。

read.csv('c:/r4r/co2.csv') # 正确。

read.csv('c:\\r4r\\co2.csv') # 正确。

找不到对象(object not found)

这并不意味着R在抱怨他自己的单身问题,而是说明某个变量并不存在。Windows用户常见的错误是忘记了R对变量名的大小写是敏感的,x和X是两个不同的变量,例如:

pm25 <- 40
PM25 + 1
## Error in eval(expr, envir, enclos): object 'PM25' not found

被赋值的是pm25,而不是PM25,做加法的时候当然找不到后者的值了。

括号用错或不完整导致各种意想不到的错误

R中的圆括号、方括号、花括号各自有不同的含义(见小贴士5.1)。如果用了不该用的括号,那么R运行时会出现难以预料的错误。例如:

x <- 1:6
x{1}
## Error: <text>:2:2: unexpected '{'
## 1: x <- 1:6
## 2: x{
##     ^

我们想调用x里的第一个元素,应该用方括号x[1]。错用花括号后,R的错误提示是“意外的花括号”。这个提示是明显的,告诉你括号用错了。但大多数情况下,是下面这种提示:

x(1)
## Error in x(1): could not find function "x"

这里,我们错用了圆括号后,R的错误提示是“找不到方程x”。R误以为你把x当方程用,不会提示你错用了括号。

另一个常见错误是括号不配对或配对不完整,也会导致无法预料的错误。

要避免这种错误,方法很简单,RStudio默认是在输入括号时自动补成对儿的,所以输入时一般不会出现问题,只要记得删除时也成对儿删掉就行了。另外,如果配对儿出现问题,RStudio会用红色标记来提示该行的括号有问题。

求和、求平均用sum()和mean()得到的结果是 NA

实际数据里常有缺失值,R默认以NA来表示(Not Available的缩写)。这样的向量在很多函数里要特殊对待,例如:

x <- c(1, 3, NA, 4)
mean(x)
## [1] NA

我们用F1小助理看一下mean()函数的帮助信息,会发现函数参数里有个na.rm,默认值为FALSE,即“不删除缺失数据”。改为’na.rm = TRUE’就行了,

mean(x, na.rm = TRUE)
## [1] 2.666667

注意,这种情况下求平均值,向量的长度是以删除缺失值后计算的。

很多函数都有这个参数,用之前记得查看帮助。

别人发给我的 .r 或 .Rmd 文件,在 RStudio 里打开有乱码

问问是不是里面有英文之外的字符,例如中文的注释等。如果是的话,很有可能是别人在生成代码文件时用了不同的编码。

在RStudio的界面点击File – Reopen with Encoding,换成别的编码试试看。

为了减少这种问题,建议大家生成代码文件时都选择UTF-8编码,点击File – Save with Encoding 选中UTF-8即可。

箭头赋值号 <- 与小于号 <

如果不注意留空格,新手有时候会因为混淆箭头赋值号与小于号而得到意外错误,例如:

x <-1
x < -1
x < - 1

上面这三个例子里,哪个是把x赋值为1,哪个是判断x是否小于-1?

为了杜绝这种无聊错误,建议在RStudio使用alt+_来输入箭头符号,会自动在箭头前后加空格。或者干脆用等号。

用read.table读一个几万行的数据文件,结果只读进去一千多行,提示我还有多少行没读入

R处理大数据文件时,受电脑的虚拟内存和地址限制,解决的方法有很多68,例如删除不再用的对象、尽量使用向量计算、用矩阵替代吃内存的数据框等。限于篇幅,本书对这个问题不展开了,请上网搜索“R语言 大数据集”。

运行blogdown::install_hugo()错误,显示“无法与服务器建立连接”

这个问题在国内出现过,出错信息一般是:

Error in download.file(url, ...):
  cannot open URL 'https://github.com/spf13/hugo/release/....'

一般情况下,是你的电脑所处的网络环境造成的。试着换个地方联网。

我在论坛发帖提问求助,为何没有人帮我解答?

有以下几种可能:

  1. 你的问题太难,没人知道怎么解答。这种情况下建议你耐心等待,或者换个论坛求助。

  2. 你问的方式不够礼貌。看看有没有用“请”字。回忆一下,上次别人帮你解答问题后,你有没有提供反馈,比如对别人说“谢谢”。帮你的人如果得不到回应,下次就不会再帮你。

  3. 你的标题没写清楚。比如发帖的标题是“菜鸟求助!紧急!”。这种帖子基本没人点开看内容。用尽量简短的语句在标题里陈述问题,节省别人的时间,例如标题写为“[求助]运行blogdown::install_hugo()错误,显示’无法与服务器建立连接’”。

  4. 你的正文里没有把问题表述清楚,或者问得太笼统。别人无法快速看懂你的问题,自然没法解答。例如“我的数据文件没法读进R,怎么办?”这样得到的回答只能是“去看书”。尽量把问题的来龙去脉说清楚,例如附上那个没法读取的数据文件的下载链接。

  5. 你没有给出示例代码。别人一般不会花时间从零开始为你写代码。如果没法快速重现你的故障,就不会回答你。尽量贴出你的代码,让别人只需拷贝粘贴过去,就能直接运行重现你的问题。

  6. 你没有说清楚你的软件运行环境。有些问题是跟运行环境有关的。你的 R 是什么版本?操作系统是什么?加载了那些扩展包?如果你不确定是否跟运行环境有关,那么保险起见,把你的运行环境信息贴出来,让别人帮你判断。R 专门提供了两个函数来获取运行环境信息:

sessionInfo()
devtools::session_info()

与人方便,自己方便。在论坛上,没有任何人有义务帮你解决问题。所以,降低你的期望值,并且换位思考一下,站在别人角度来看你的求助帖,就知道应该如何提问了。只有先为别人节省时间,才能为自己节省时间,从而快速得到别人的帮助。

习题参考答案

这里给出了各章练习的参考答案以及详细注释。正如我们前文所说的,每道题的解答方式都不是唯一的,只要得到想要的答案就可以了。

参考答案里,我们使用了timeDate (Team et al. 2015)、fun (Xie, Wei, and Qiu 2011)、animation 和openair (Carslaw and Ropkins 2012)等扩展包。

练习1.1参考答案

# 方案1
365 %% 7
365 %/% 7

# 方案2
floor(365/7) # 向下取整函数
365 - floor(365/7)
# 与floor() 属于同一家族的还有:
# ceiling(), trunc(), round(), signif()

练习1.2参考答案

x <- c(97, 80, 64, 91, 87, 100, 128, 144, 150, 150, 150, 106, 
       78, 68, 62, 46, 55, 68, 84, 92, 95, 108, 128, 138)
plot(x)

# 方案1
max(x)
min(x)
mean(x)

# 方案2
summary(x)[c(1, 4, 6)]

练习2.1参考答案

mydata2 <- as.data.frame(t(matrix(
  co2, 12, dimnames = list(month.abb, unique(floor(time(co2)))))))  
mydata2$year <- as.numeric(rownames(mydata2))
x1995 <- mydata2['1995', 2:13]

# 方案1
max(x1995)
min(x1995)

# 方案2
range(x1995) # range()返回取值范围。

练习3.1参考答案

mydata2 <- as.data.frame(t(matrix(
  co2, 12, dimnames = list(month.abb, unique(floor(time(co2)))))))  
mydata2$year <- as.numeric(rownames(mydata2))
mydata2$mean <- rowMeans(mydata2[, 2:13])

# 方案1:用字符指定数据点形状和颜色
plot(x = mydata2$year, y = mydata2$mean, 
     type = 'p', pch = '▲', col = 'yellow')

# 方案2:用数字指定数据点形状和颜色
plot(x = mydata2$year, y = mydata2$mean, 
     type = 'p', pch = 17, col = colors()[142])

练习3.2参考答案

x <- mydata2$year
y <- mydata2$Sep
plot(x = x, y = y)
abline(v = min(x):max(x), h = min(y):max(y), col = 'grey')
text(x, y, labels = y, col = 'red', pos = c(2, 4))  
# pos 参数来指定文字位于给定坐标的哪一侧,
# pos 取值可以是1,2,3,4。

练习3.3参考答案

x <- mydata2$year[1:6]
y <-  mydata2$Sep[1:6]

# 方案1:逐个画图
pdf('c:/r4r/9in1.pdf')
par(mfrow = c(3,3), cex = 1.2, mar = c(3, 2, 0.5, 1))
plot(x = x, y = y, type = 'p')
legend('topleft', legend = 'p', 
       cex = 0.8, bty = "n", text.col = 'blue')
plot(x = x, y = y, type = 'l')
legend('topleft', legend = 'l', 
       cex = 0.8, bty = "n", text.col = 'blue')
plot(x = x, y = y, type = 'b')
legend('topleft', legend = 'b', 
       cex = 0.8, bty = "n", text.col = 'blue')
plot(x = x, y = y, type = 'c')
legend('topleft', legend = 'c', 
       cex = 0.8, bty = "n", text.col = 'blue')
plot(x = x, y = y, type = 'o')
legend('topleft', legend = 'o', 
       cex = 0.8, bty = "n", text.col = 'blue')
plot(x = x, y = y, type = 'h')
legend('topleft', legend = 'h', 
       cex = 0.8, bty = "n", text.col = 'blue')
plot(x = x, y = y, type = 's')
legend('topleft', legend = 's', 
       cex = 0.8, bty = "n", text.col = 'blue')
plot(x = x, y = y, type = 'S')
legend('topleft', legend = 'S', 
       cex = 0.8, bty = "n", text.col = 'blue')
plot(x = x, y = y, type = 'n')
legend('topleft', legend = 'n', 
       cex = 0.8, bty = "n", text.col = 'blue')
dev.off()

# 方案2:用循环结构以简化操作
par(mfrow = c(3,3), cex = 1.2, mar = c(3, 2, 0.5, 1))
for (i in c("p", 'l', "b", "c", "o", "h", "s", "S", "n")) {
  plot(x = x, y = y, type = i)
  legend('topleft', legend = i, 
         cex = 0.8, bty = "n", text.col = 'blue')
}

练习4.1参考答案

wp <- as.data.frame(WorldPhones)
m0 <- lm(wp$Asia ~ wp$Europe + 0)
summary(m0)
plot(x = wp$Europe, y = wp$Asia, pch = 19)  
abline(m0, col = "red")
legend("bottomright", pch = c(19, NA), lty = c(NA, 1),
       legend = c("Data", "Linear fit"), 
       col = c("black", "red"), bty = 'n')
eqlm <- expression(italic(y) == 0.1854 * italic(x))
eqr2 <- expression(italic(R) ^ 2 == 0.9856)
eqn <- expression(italic(n) == 7)
text(x = 23000, y = 7000, labels = eqlm, adj = 0)
text(x = 23000, y = 6000, labels = eqr2, adj = 0)
text(x = 23000, y = 5000, labels = eqn, adj = 0)

练习4.2参考答案

# 只需将plot()函数的ylab参数改为:
ylab = expression(CO[2])

练习4.3参考答案

x <- seq(0, 50, 1)
y <- runif(1, 5, 15) * exp(-runif(1, 0.01, 0.05) * x) +
  rnorm(51, 0, 0.5)
a_start <- 14
b_start <- - log(6/a_start) / 50
m <- nls(y ~ a * exp(-b * x), 
         start = list(a = a_start, b = b_start))
plot(x, y)
lines(x, predict(m), col = 'darkgreen') 
# predict()函数返回预测值
eqnls <- expression(italic(y) == 15.18 * 
                      italic(e) ^ {-0.04786 * italic(x)})
text(10, 4, eqnls)
legend("topright", pch = c(1, NA), lty = c(NA, 1), 
       legend = c("Data", "Non-linear fit"), 
       col = c("black", "darkgreen"), bty = 'n')

练习5.1参考答案

# 方案1
for (i in seq(from = 1, to = 100, by = 2)) print(i)

# 方案2
print(seq(from = 1, to = 100, by = 2)) 
# seq()函数本来内藏的逻辑就是循环

练习5.2参考答案

x <- c(2, 3, 5)
y <- c(1, 2, 3, 4)
m <- matrix(nrow = length(x), ncol = length(y))
for (i in 1:length(x)){
  for (j in 1:length(y)){
    m[i,j] = x[i] * y[j]
  }
}
m

练习5.3参考答案

for (i in 2:13) print(colMeans(mydata2[, i]))

练习5.4参考答案

wp <- as.data.frame(WorldPhones)
wp$year <- as.numeric(rownames(wp))
mydata3 <- data.frame(
  nphone = unlist(wp[, 1:7]), year = rep(wp$year, 7),
  conti = rep(names(wp)[1:7], each = nrow(wp)))
boxplot(mydata3$nphone ~ mydata3$year)
boxplot(mydata3$nphone ~ mydata3$conti)

练习5.5参考答案

tapply(mydata3$nphone, mydata3$year, max)
tapply(mydata3$nphone, mydata3$year, min)
tapply(mydata3$nphone, mydata3$year, median)

练习6.1参考答案

m <- 6:1
n <- c(3, 5, 6)
for (mi in m) print(mi == n)

练习6.2参考答案

# 方案1
for (i in 1:100){
  if (i %% 2 == 0 & i %% 3 == 0) print(i) 
}

# 方案2
i <- 1:100
i[i %% 2 == 0 & i %% 3 == 0]

# 方案3
seq(from = 6, to = 100, by = 6)

练习6.3参考答案

z <- 2
for (i in 3:10000) {
  j <- 2:(i-1)
  if (sum(i %% j == 0) == 0) z <- c(z, i)
}
z
# 这个方案完全按照素数的定义来逐个判断,虽管用,但效率低。
# 请试着用其他方案来提高运算效率。

练习6.4参考答案

x <- c(97, 80, 64, 91, 87, 100, 128, 144, 150, 150, 150, 106, 
       78, 68, 62, 46, 55, 68, 84, 92, 95, 108, 128, 138)
hour <- 0:23
hour[x == max(x)]

练习6.5参考答案

hour[x > 75]

6.3节参考答案

# 方案1
year = 2017: 2026
method = "Meeus"
calendar = "Gregorian"

Y <- year
if (method == "Gauss") # 以下为高斯算法,适用于 1583 -- 2299 年
{
  if (calendar == "Gregorian") # 公历(天主教)
  {
    k <- (Y - 1500) %/% 100 + 1
    M <- c(22,22,23,23,24,24,24,25)[k]
    N <- c(2,2,3,4,5,5,6,0)[k]
    
  } else if (calendar == "Julian") # 儒略历(东正教)
  {
    M <- 15; N <- 6
  } else
  {
    print("sorry, the calendar does not exist. 
          use method = 'Gregorian' or 'Julian'")
  }
  a <- Y %% 19
  b <- Y %% 4
  c <- Y %% 7
  d <- (19 * a + M) %% 30
  e <- (2 * b + 4 * c + 6 * d + N) %% 7
  computus.date <- ifelse(d + e < 10,
                          paste("3-", d + e + 22, sep = ""),
                          paste("4-", d + e - 9, sep = ""))
  if (computus.date == "4-26") computus.date <- "4-19"
  if (computus.date == "4-25" & d == 28 & e == 6 & a > 10) 
    computus.date <- "4-19" # 高斯,I 服了 U!
  computus <- paste(Y, computus.date, sep = "-")
} else if (method == "Meeus") # 以下为Meeus 算法
{
  if (calendar == "Gregorian") # 公历(天主教)
  {
    a <- Y %% 19
    b <- Y %/% 100
    c <- Y %% 100
    d <- b %/%4
    e <- b %%4
    f <- (b + 8) %/% 25
    g <- (b - f + 1) %/%3
    h <- (19 * a + b - d - g + 15) %% 30
    i <- c %/% 4
    k <- c %% 4
    L <- (32 + 2 * e + 2 * i - h - k) %% 7
    m <- (a + 11 * h + 22 * L) %/% 451
    month <- (h + L - 7 * m + 114) %/% 31
    day <- ((h + L - 7 * m + 114) %% 31) + 1
  } else if (calendar == "Julian") # 儒略历(东正教)
  {
    a <- Y %% 4
    b <- Y %% 7
    c <- Y %% 19
    d <- (19 * c + 15) %% 30
    e <- (2 * a + 4 * b - d + 34) %% 7
    month <- (d + e + 114) %/% 31
    day <- ((d + e + 114) %% 31) + 1
  } else
  {
    print("sorry, the calendar does not exist. 
          use method = 'Gregorian' or 'Julian'")
  }
}
computus <- paste(Y, month, day, sep = "-")
computus

# 方案2: 使用别人写好的函数(扩展包)。
if(!require("timeDate")) install.packages("timeDate") 
require("timeDate")
Easter(year = 2017:2026)

练习8.1参考答案

write.csv(WorldPhones, file = 'c:/r4r/wp.csv')
wp_path <- "C:/r4r/wp.csv"
file.show(wp_path)
wp <- read.csv(file = wp_path)
summary(wp)
plot(wp)
names(wp)[1] <- 'year'
rownames(wp) <- wp$year

练习8.2参考答案

wp$decade <- c('1950s', '1950s', '1950s', '1950s', '1950s',
               '1960s', '1960s')
str(wp)

练习8.3参考答案

m <- matrix(data = 1:30, nrow = 5)

练习8.4参考答案

wp_mt <- as.matrix(wp)
str(wp_mt) 
# 由于矩阵里的元素要求全部是同一类型,
# 所以数字全部强制转换成了字符。
wp['1956', 'Europe']
wp_mt['1956', 'Europe']
wp[, c('Asia', 'Europe')]
wp_mt[, c('Asia', 'Europe')]
wp[c(2, 4, 5), ]
wp[-c(2, 4, 5), ]

练习8.5参考答案

annualsum <- rowSums(wp[, 2:7])
annualdiff <- diff(annualsum)
annualdiffeach <- apply(wp[, 2:7], MARGIN = 2, diff)
annualrate <- annualdiff/annualsum[1:6]
annualrateeach <- apply(wp[, 2:7], MARGIN = 2, 
                        function(x) diff(x)/x[1:6]) 
# apply用于自定义函数。见第8章。

练习8.6参考答案

par(mfrow = c(2, 1), mar = c(0, 3, 3, 1))
plot(wp$year, wp$Asia, type = 'l', xlim = c(1951, 1961),
     axes = FALSE, xlab = '', ylab = 'Phone Asia')
axis(2)
box()
par(mar = c(3, 3, 0, 1))
plot(wp$year[1:6], annualrateeach[, 'Asia'], type = 'l',
     xlim = c(1951, 1961), 
     xlab = 'year', ylab = 'Increase rate')
dev.off()

练习8.7参考答案

myylim <- range(wp[, 2:8])
mycol <- rainbow(7)
plot(wp$year, wp[, 2], col = mycol[1], type = 'l', 
     xlab = 'year', ylab = 'Phone number', ylim = myylim)
for (i in 3:8) 
  lines(wp$year, wp[, i], col = mycol[i-1])
legend('topleft', legend = names(wp)[2:8], 
       lty = 1, col = mycol, bty = 'n')

练习8.8参考答案

par(mfrow = c(3, 3), mar = c(4, 4, 0.1, 0.1))
for (i in 2:8) {
  plot(wp$year, wp[, i], col = mycol[i-1], 
       xlab = 'year', ylab = names(wp)[i])
  m <- lm(wp[, i] ~ wp$year)
  a1 <- m$coefficients[1]
  a2 <- m$coefficients[2]
  abline(m)
  legend('topleft', bty = 'n', 
         as.expression(substitute(y == a + b * x,
                                  list(a = a1, b = a2))))
}

练习8.10参考答案

# 方案:穷举
for (Aa in 1:9){
  for (Bb in c(0:9)[!0:9 %in% Aa]){
    for (Cc in c(0:9)[!0:9 %in% c(Aa, Bb)]){
      for (Dd in c(1:9)[!1:9 %in% c(Aa, Bb, Cc)]){
        for (Ee in c(0:9)[!0:9 %in% c(Aa, Bb, Cc, Dd)]){
          for (Ff in c(1:9)[!1:9 %in% c(Aa, Bb, Cc, Dd)]){
            if ((100 * Aa + 10 * Bb + Cc) * (Dd * 10 + Cc) == 
                Ff * 1000 + Dd * 100 + Bb * 10 + Cc &
                (100 * Aa + 10 * Bb + Cc) * Cc == 
                Dd * 1000 + Ee * 100 + Aa * 10 + Cc &
                (100 * Aa + 10 * Bb + Cc) * Dd == 
                700 + Ee * 10 + Dd &
                Dd * 1000 + Ee * 100 + Aa * 10 + Cc + 7000 + 
                Ee * 100 + Dd * 10 == Ff * 1000 + Dd * 100 + 
                Bb * 10 + Cc) 
              print(c(Aa, Bb, Cc, Dd, Ee, Ff))
          }
        }
      }
    }
  }
}
# 这里给出的方法是穷举,把1001到9999之间的所有数都试了一遍。
# 这是计算机擅长的方式。

# 方案2
# 小学生的解题思路是这样的:
# ABC乘以C等于DEAC,C只能是5或6,
# 但根据ABC乘以D等于7ED,所以C不可能是5,C = 6。
# D + 7 = F,D只能是1或2,但C乘以D末尾是C,
# 所以D = 2,F = 9, E = 1。
# 由于C = 6,D = 2,那么 A 只能是3,B = 5。

练习8.11参考答案

d <- 1
left <- 125
leftc <- left
drop <- 1
dropc <- drop
drop <- drop + 1
while (left != drop) {
  d <- d + 1
  left <- left - drop
  leftc <- c(leftc, left)
  dropc <- c(dropc, drop)
  if (left < drop + 1) drop <- 1 else drop <- drop + 1
}
plot(leftc, ylim = c(0, 123))
points(dropc, col = 'red')
# 仍然是穷举法。
# 小学生的解题思路应该是:125 = 120 + 3 + 1 + 1
# 三项对应着15天,2天,1天,1天,所以总共19天掉完。

练习9.1参考答案

kaipingfang <- function(x) return(sqrt(x)) 

练习9.2参考答案

cv <- function(x) sd(x)/mean(x) # 省略了return()

练习9.3参考答案

# 只需将第6.3节参考答案代码的前三行删掉,
# 其他代码放进下面的花括号里即可。
computus <- function(year, method, calendar) {}

练习9.6参考答案

install.packages('animation')
library(animation)
demo("fireworks") # 会用网页浏览器打开一个动画。
citation("animation") # 看看作者。

练习9.7参考答案

install.packages('openair')
library(openair)
example(windRose)
citation('openair')

9.5参考答案

install.packages('fun')
library(fun)
if (.Platform$OS.type == "windows") x11() else 
  x11(type = "Xlib")
mine_sweeper()
demo(package = 'fun')

练习10.1参考答案

p1 <- 'Pack my box with five dozen liquor jugs'
p1 <- tolower(p1)
dup1 <- table(strsplit(gsub(' ','', p1), ''))
dup1[dup1>1]

练习10.2参考答案

# 提示:
# 1. 跟千字文的处理方法类似
# 2. 中华字经的原文可以在网上搜
# 3. 常用汉字3500字可以在网上搜,由国务院颁布

练习11.2参考答案

us <- read.csv("C:/r4r/us.csv")
cols <- rainbow(nlevels(us$state)) # create 49 rainbow cols
plot(us$lon, us$lat, col = cols[us$state], pch = 20)
lon.median <- tapply(us$lon, us$state, median)
lat.median <- tapply(us$lat, us$state, median)
text(labels=levels(us$state), 
     x=lon.median, y=lat.median, cex=0.5, col = 'White')
abline(h = seq(from = 25, to = 50, by = 5), col = 'grey')
unique(us$state[us$lat > 34.9 & us$lat < 35.1])

练习11.3参考答案

timez <- as.factor(us$lon %/% 15)
mycol <- rainbow(nlevels(timez))[timez]
plot(us$lon, us$lat, col = mycol, pch = 20)

练习11.4参考答案

# 只需把mycol一行改为:
mycol <- rev(rainbow(nlevels(aqilevel)))[aqilevel]

练习12.1参考答案

format(Sys.time(), '%j')

练习12.2参考答案

bd <- '1994-09-22 20:30:00'
bdtime <- strptime(x = bd, format = '%Y-%m-%d %H:%M:%S', 
                   tz = "Asia/Shanghai")
bdtime$yday

练习12.3参考答案

format(bdtime, '%c')

练习12.4参考答案

difftime(Sys.time(), bdtime, units = 'days')
difftime(Sys.time(), bdtime, units = 'hours')
difftime(Sys.time(), bdtime, units = 'secs')

练习12.5参考答案

bdyears <- seq(from = 1994, by = 1, length.out = 101)
bd100 <- paste(bdyears, '-09-22 20:30:00', sep = '')
bd100 <- strptime(x = bd100, format = '%Y-%m-%d %H:%M:%S',
                  tz = "Asia/Shanghai")
bdwd <- bd100$wday
plot(x = bdyears, y = bdwd)
abline(v = seq(from = 1995, by = 5, to = 2100), 
       col = 'grey')
sum(bdwd == 0)

练习13.2参考答案

download.file(url = "http://dapengde.com/r4rookies/obs.zip", 
              destfile = "C:/r4r/obs.zip")
unzip(zipfile = "C:/r4r/obs.zip", exdir = "C:/r4r")

stn <- 50
obsdir <- 'C:/r4r/obs'
obsfilefull <- dir(obsdir, full.names = TRUE)
output <- NULL
for (k in 1:length(obsfilefull))
{
  input <- read.table(obsfilefull[k], header = FALSE, 
                      skip = 2, sep = "")
  obstimestr <- strsplit(
    readLines(obsfilefull[k])[2], ' ')[[1]]
  obstime <- paste(
    '20', obstimestr[3], '-', obstimestr[5], '-',
    obstimestr[7], ' ', obstimestr[9], sep = '')
  output_new <- input[which(
    input[, 1] >= stn * 1000 & 
      input[, 1] < (stn + 10) * 1000), c(1, 4)]
  output_new$time <- obstime
  output <- rbind(output, output_new)
}
output

练习13.3参考答案

output$stn <- as.factor(output$V1)
boxplot(output$V4 ~ output$stn)

Adler, Daniel, Duncan Murdoch, and others. 2017. Rgl: 3D Visualization Using Opengl. https://CRAN.R-project.org/package=rgl.

Allaire, JJ, Joe Cheng, Yihui Xie, Jonathan McPherson, Winston Chang, Jeff Allen, Hadley Wickham, Aron Atkins, and Rob Hyndman. 2016. Rmarkdown: Dynamic Documents for R. https://CRAN.R-project.org/package=rmarkdown.

Bivand, Roger, and Nicholas Lewin-Koh. 2017. Maptools: Tools for Reading and Handling Spatial Objects. https://CRAN.R-project.org/package=maptools.

Bivand, Roger, Tim Keitt, and Barry Rowlingson. 2016. Rgdal: Bindings for the Geospatial Data Abstraction Library. https://CRAN.R-project.org/package=rgdal.

Carslaw, David C., and Karl Ropkins. 2012. “Openair — an R Package for Air Quality Data Analysis.” Environmental Modelling & Software 27–28 (0): 52–61. doi:10.1016/j.envsoft.2011.09.008.

Dragulescu, Adrian A. 2014. Xlsx: Read, Write, Format Excel 2007 and Excel 97/2000/Xp/2003 Files. https://CRAN.R-project.org/package=xlsx.

Gohel, David. 2017. ReporteRs: Microsoft Word and Powerpoint Documents Generation. https://CRAN.R-project.org/package=ReporteRs.

Lang, Dawei. 2017. LeafletCN: An R Gallery for China and Other Geojson Choropleth Map in Leaflet. https://CRAN.R-project.org/package=leafletCN.

Lemon, J. 2006. “Plotrix: A Package in the Red Light District of R.” R-News 6 (4): 8–12.

Petzoldt, Thomas, and Karsten Rinke. 2007. “Simecol: An Object-Oriented Framework for Ecological Modeling in R.” Journal of Statistical Software 22 (9): 1–31. http://www.jstatsoft.org/v22/i09.

R Core Team. 2016. R: A Language and Environment for Statistical Computing. Vienna, Austria: R Foundation for Statistical Computing. https://www.R-project.org/.

Sarkar, Deepayan. 2008. Lattice: Multivariate Data Visualization with R. New York: Springer. http://lmdvr.r-forge.r-project.org.

Team, Rmetrics Core, Diethelm Wuertz, Tobias Setz, Yohan Chalabi, Martin Maechler, and Joe W. Byers. 2015. TimeDate: Rmetrics - Chronological and Calendar Objects. https://CRAN.R-project.org/package=timeDate.

Wickham, Hadley. 2009. Ggplot2: Elegant Graphics for Data Analysis. Springer-Verlag New York. http://ggplot2.org.

———. 2017. Stringr: Simple, Consistent Wrappers for Common String Operations. https://CRAN.R-project.org/package=stringr.

Xie, Yihui. 2016. Bookdown: Authoring Books and Technical Documents with R Markdown. Boca Raton, Florida: Chapman; Hall/CRC. https://github.com/rstudio/bookdown.

———. 2017. Blogdown: Create Blogs and Websites with R Markdown. https://github.com/rstudio/blogdown.

Xie, Yihui, Taiyun Wei, and Yixuan Qiu. 2011. Fun: Use R for Fun. https://CRAN.R-project.org/package=fun.

Zeileis, Achim, the R community. Contributions (fortunes and/or code) by Torsten Hothorn, Peter Dalgaard, Uwe Ligges, Kevin Wright, Martin Maechler, Kjetil Brinchmann Halvorsen, et al. 2016. Fortunes: R Fortunes. https://CRAN.R-project.org/package=fortunes.

Zhao, Peng. 2017a. Beginr: Functions for R Beginners. https://CRAN.R-project.org/package=beginr.

———. 2017b. Bookdownplus: Generate Varied Types of Books and Documents with R ’Bookdown’ Package. https://CRAN.R-project.org/package=bookdownplus.

———. 2017c. Mindr: Convert Files Between Markdown or Rmarkdown Files and Mindmaps. https://CRAN.R-project.org/package=mindr.

References

Team, Rmetrics Core, Diethelm Wuertz, Tobias Setz, Yohan Chalabi, Martin Maechler, and Joe W. Byers. 2015. TimeDate: Rmetrics - Chronological and Calendar Objects. https://CRAN.R-project.org/package=timeDate.

Xie, Yihui, Taiyun Wei, and Yixuan Qiu. 2011. Fun: Use R for Fun. https://CRAN.R-project.org/package=fun.

Carslaw, David C., and Karl Ropkins. 2012. “Openair — an R Package for Air Quality Data Analysis.” Environmental Modelling & Software 27–28 (0): 52–61. doi:10.1016/j.envsoft.2011.09.008.