简体   繁体   English

优化R中的循环

[英]Optimizing for loop in R

I have been doing a lot of research and I think I am missing something when it comes to nested for loops in R. I have two dataframes - one that contains observations and locations where I want to write the outputs and another that has the variable names I am looping through. 我一直在做很多研究,我想在R中嵌套循环时会丢失一些东西。我有两个数据框-一个包含观察值和位置,我想在其中写输出,另一个包含变量名我正在遍历。 Right now the loop works, but it is taking 14+ hours to loop through 200 rows which seems a bit excessive. 目前,该循环有效,但是要遍历200行需要14个多小时,这似乎有点多余。 Granted I am preforming 12 separate permutations (100 times) at each row, though I would ideally like to do >1000+ permutations. 当然,我希望每行执行12个单独的排列(100次),尽管我理想情况下希望执行> 1000+个排列。 Is there a more efficient way of preforming this for loop? 有没有更有效的方法来执行此for循环? When I run a single observation it takes vey little time to complete (sub 2 seconds), which makes me beg the question that there should be a better way to accomplish this task. 当我进行单个观察时,只需很少的时间(不到2秒)即可完成,这使我感到困惑的是,应该有一种更好的方法来完成此任务。 Any help you can give in optimizing this code would be greatly appreciated! 您可以在优化此代码方面提供的任何帮助将不胜感激! thanks! 谢谢!

The main dataset is attached(fbfm.xlsx) which is called fm.std https://www.dropbox.com/s/vmd8d05yxds93j6/fbfm.xlsx?dl=0 附加了主要数据集(fbfm.xlsx),称为fm.std https://www.dropbox.com/s/vmd8d05yxds93j6/fbfm.xlsx?dl=0

library(rothermel)
u.val<-c(5,10,15,25,35,45,55,65,75,85,95,100)
unames <- data.frame(u=u.val,ros.nam=paste("u",u.val,"_ROS",sep=""), stringsAsFactors = FALSE)
ros.out<-data.frame(fm.std)
for (i in 1:dim(unames)[1]){
     ros.out[,unames[i,'ros.nam']]<-999
          }
ros.out <- as.vector(ros.out)
fm.std <- as.vector(fm.std)
for (i in 1:dim(ros.out)[1]){
   ros.out[i,1:32]
     for (u in 1:dim(unames)[1]){
         ros.out[i,unames[u,'ros.nam']]<-mean(rosunc(modeltype=fm.std[i,'Fuel_Model_Type'], #Dyanmic or static model
                                            w=fm.std[i,4:8], # fuel loads (1, 10, 100, herb, and shrub)
                                            s=fm.std[i,9:13], # SAV measurements
                                            delta=fm.std[i,14], #fuel bed depth
                                            mx.dead=fm.std[i,15], # dead fuel mositure of extinction
                                            h=fm.std[i,16:20], # heat content for fuel classes
                                            m=fm.std[i,c(25,24,23,26,30)], #percent moisture of fuel classes
                                            u = unames[u,'u'],
                                            slope=0,
                                            sdm=0.3,
                                            nsim=100) ) #wind and slope of 0 }}

Consider a more vectorized sapply() approach passing in two vectors, u.val and 1:nrow(fm.std) . 考虑传入两个向量u.val1:nrow(fm.std)的更具向量化的sapply()方法。 This will build a 200-row, 12-column matrix that you can convert to a dataframe and then cbind to original dataframe. 这将建立一个200行,12列的矩阵,您可以将其转换为数据cbind ,然后cbind为原始数据cbind

ucols <- sapply(u.val, 
                function(x, y){
                   mean(rosunc(modeltype=fm.std[y,'Fuel_Model_Type'],  # Dyanmic or static model
                               w=fm.std[y,4:8],       # fuel loads (1, 10, 100, herb, and shrub)
                               s=fm.std[y,9:13],      # SAV measurements
                               delta=fm.std[y,14],    # fuel bed depth
                               mx.dead=fm.std[y,15],  # dead fuel mositure of extinction
                               h=fm.std[y,16:20],     # heat content for fuel classes
                               m=fm.std[y,c(25,24,23,26,30)],     # percent moisture of fuel classes
                               u=x,
                               slope=0,
                               sdm=0.3,
                               nsim=100))
                }, 1:nrow(fm.std))

# CONVERT MATRIX TO DATA FRAME
ucols <- data.frame(ucols)
# RENAME COLUMNS
names(test) <- paste("u",u.val,"_ROS",sep="")

# BIND COLUMNS TO ORIGINAL DATA FRAME
ros.out <- cbind(fm.std, ucols)

Alternatively, consider using outer() with transpose, t() to achieve the 200-row and 12-col matrix. 或者,考虑将outer()与转置t()以实现200行12 col矩阵。

ucols <- t(outer(u.val, 1:nrow(fm.std), 
                    function(x, y){
                         mean(rosunc(...))
                    }
           ))
...

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM