rcpp包 c语言的优化,如何提高备受诟病的R的运行速度

说到R,人们除了赞美它漂亮简洁的做图功能外,就是抱怨它的运行速度问题。做为常规使用,好比数据整理分析,统计计算或者做图等,或许没有感受到它的运行速度有问题。可是若是数据量很大,像基因组数据,那么运行起来就尤为慢了。特别是对于循环语句,犹如老牛拉破车,因此在数据量很大的状况下,尽可能不要在R中使用循环语句。html

那么循环语句在R中会慢到什么地步?咱们经过R语言和C语言的比较就能看出一些端倪。编程

咱们假设有这么两个数据框,以下图。咱们要判断每个pos中的数据(4,15,19,27)是否落在第一个数据框的数据区间内(2-5,7-11,17-20,23-28,32-39)。这样咱们就会用到两个嵌套for循环,对第二个数据框中的每个数,依次比对第一个数据框中的每个数据段。app

0edf193177b3f4ad2a8cb57b0323003a.png

首先咱们使用随机数生成这么两个模拟数据框编程语言

set.seed(111)

creat_test

x

x

start = numeric()

end = numeric()

for (i in seq(1,length(x),2)){

start

end

}

test_df

return(test_df)

}

# create first data frame, using length = 7,000,000, segments = 20,000

test_data

# create second data frame, sequence data

sequence

sequence$x

自此,咱们有了两个测试数据框,第一个test_data里面有20万条观测,第二个sequence里面有400个观测,那么咱们首先经过R中的for循环来判断这400个观测时候落在来第一个数据框中数据段内。ide

# using R loop to see if sequence in test_data range

R_time

num_in

for (i in 1:nrow(sequence)){

for (j in 1:nrow(test_data)){

if (sequence[i,1] > test_data[j,1] & sequence[i,1] < test_data[j,2]){

num_in

break

}

}

}

print(num_in)

}

system.time(R_time(sequence,test_data))

这段代码中两个for循环,大概运行来:函数

769c59aaf40df5d894764fbb6247c77e.png

下面咱们看一看在C语言中完成这段代码须要多长时间。本人并不了解C语言,可是Rcpp包提供了在R中写C代码的可能,因此使用Rcpp完成上述功能以下:oop

# using Rcpp

library(Rcpp)

cppFunction('

int Rcpp_time(DataFrame sequence, DataFrame test_data){

IntegerVector start=test_data["start"];

IntegerVector end=test_data["end"];

IntegerVector pos=sequence["x"];

int seq_size=sequence.nrow();

int test_size=test_data.nrow();

int num_in=0;

for(int i=0; i<=seq_size; i++){

for(int j=0; j<=test_size; j++){

if(pos[i]>start[j] && pos[i]

num_in++;

break;

}

}

}

return num_in;

}

')

system.time(Rcpp_time(sequence,test_data))

而这段代码的运行时间仅仅为:测试

69f4bfa9702b1137b3e26d8e8d083172.png

能够看出,一样的一段代码,获得相同的结果,在R中运行的时间是在C中运行时间的数万倍!什么概念:code

在R中你要等1个多小时,在C中你在1秒内就完成!orm

固然这也很好理解,毕竟相对于C来说,R属于高级编程语言,并且是解释型语言,没有C的编译过程,因此R会针对每个for循环一一执行,这也下降了速度。

那么问题来了,应该怎样提升R的运行速度呢?

一、避免使用for循环,尤为是数据量特别大的时候;

二、避免数据的复制,使用%>%之类的管道操做;

三、使用一些更快的R包处理数据,好比data.table;

四、使用apply、lapply等之类的函数代替for;

五、使用Rcpp编写C语言函数;

六、使用多核并行计算(能够经过lapply来实现);

能够参考http://adv-r.had.co.nz/Performance.html

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值