前三章中列出的大多数示例代码都很短,并没有涉及到复杂的操作。从本章开始将会把前面介绍的数据结构组合起来,构成真正的程序。大部分程序是由条件语句和循环语句控制,R 语言中的条件语句(if-else)和 C 语言中类似此处就不再介绍,循环语句包括 for
和 while
控制块。循环是社交网络分析的主旋律,比如使用 for
循环遍历分析网络中的每一个节点。当网络规模足够大时,并行处理又变得十分必要。熟练掌握本章的内容后,你的程序将会优雅而自然。
循环语句
while
while
循环作为最简单的一种循环,只要满足条件(condition 为 TRUE
),循环将会一直进行。
while (condition) {
# TODO
}
在 R 语言中还存在特殊的关键字 repeat
,在 repeat
控制块内的语句将会无限的执行。下面的示例代码效果是等价的:
repeat {
# TODO
}
while (TRUE) {
# TODO
}
for
R 语言中的 for
循环更像某些语言中的 foreach
,本质上就是遍历向量(或其他数据结构)中的元素:
for (name in vector) {
# TODO
}
下面的示例将会输出向量中的元素:
> v <- c("a", "b", "c")
> for (item in v) {
+ print(item)
+ }
[1] "a"
[1] "b"
[1] "c"
循环控制
有时当满足条件时,需要使用 break
退出循环:
while (TRUE) {
# TODO
if (condition) {
break
}
}
或者使用 next
退出当前循环(类似其他语言的 continue
):
for (name in vector) {
# TODO
if (condition) {
next
}
}
apply() 系列函数
R 语言中循环语句的执行效率是无法忍受的,这是因为循环语句是基于 R 语言本身来实现的,而向量操作是基于 C 语言实现的,所以应避免使用显式循环,使用 apply()
系列函数进行替代。举个例子,对一个矩阵的行求和,并封装一个函数,使用 for
循环应该是这样:
func1 <- function(matrix) {
row_sum <- c()
for (i in 1: nrow(matrix)) {
row_sum[i] <- sum(matrix[i, ]) # 对每一行求和
}
return(row_sum)
}
使用 sapply()
可以这样简化代码:
func2 <- function(matrix) {
return(sapply(1: nrow(matrix), function(i) { return(sum(matrix[i, ])) }))
}
下面测试一下两种方法的性能消耗:
> m <- matrix(c(1: (10000 * 10000)), nrow = 10000) # 10000x10000 的方阵
> system.time(func1(m))
用户 系统 流逝
0.79 0.00 0.79
> system.time(func2(m))
用户 系统 流逝
0.72 0.00 0.72
上面的例子说明使用 for
循环不仅代码冗余,而且 for
循环实现的计算是耗时最长的,这就是为什么要了解 apply()
系列函数的原因。apply()
系列函数本身就是解决数据循环处理的问题,为了面向不同的数据类型,不同的返回值,apply()
函数组成了一个函数族。一般使用最多的是对矩阵处理的函数 apply()
以及对向量处理的函数 sapply()
。
apply() 系列函数[1]
apply()
apply()
函数用于多维数据的处理,比如矩阵。其本质上是对 for
循环的进一步封装,并不会加快计算速度。apply()
函数的定义如下:
apply(X, MARGIN, FUN)
文章来源: 博客园
- 还没有人评论,欢迎说说您的想法!