2015-09-14 106 views
1

最近我寫了一段代碼,其行爲並不像預期的那樣。 在一個循環超過兩dataframes DF1,DF2我試圖收集在一個矩陣數據「一」 ...:lapply(list)和「for」的區別-loop

df1=data.frame(x=c(1,2),y=c(10,20)) 
df2=data.frame(x=c(4,5),y=c(40,50)) 
dlist <- list(df1,df2) 

a <- c(0,"...creation...") 
a <- rbind(a, c(0,"rbind test OK")) 

lapply(dlist, function(d) { 
    print(paste("x",d$x[1])) 
    a <- rbind(a, c(d$x[1],"data copied")) 
    }) 

a <- rbind(a, c(0,"rbind test 2 OK")) 

檢查「一」執行這些線後產生

a 
    [,1] [,2]    
a "0" "...creation..." 
    "0" "rbind test OK" 
    "0" "rbind test 2 OK" 

也就是說,lapply循環內的rbind語句沒有執行。

預期成果是:

a 
    [,1] [,2] 
a "0" "...creation..." 
    "0" "rbind test OK" 
    "1" "data copied" 
    "4" "data copied" 
    "0" "rbind test 2 OK" 

這是爲什麼?

+0

一個區別是for循環在調用時使用相同的環境; lapply(和其他類似的功能)使用他們自己的環境,就像其他功能一樣。這意味着您在'lapply()'函數中定義的'a'與您之前定義的'a'不同。請提供一個預期輸出的例子,如果你想要更多的信息 –

+0

預期的輸出將是 > a [,1] [,2] a「0」「...創建...」 「0」「rbind測試OK「 」1「」數據複製「 」4「」數據複製「 」0「」rbind test 2 OK「 – JCR

+0

請修改您的問題以包含預期輸出。 – 2015-09-14 07:21:27

回答

0

您可以修改環境與運營商<<-循環,但是這是一個非常不適當的命令式編程reflexe:

lapply(dlist, function(d) { 
    print(paste("x",d$x[1])) 
    a <<- rbind(a, c(d$x[1],"data copied")) 
}) 

一種合適的方式將繼續這樣的:

res = do.call(rbind, lapply(dlist, function(d) c(d$x[1],"data copied"))) 

a = rbind(a, res, c(0,"rbind test 2 OK")) 

# [,1] [,2]    
#a "0" "...creation..." 
# "0" "rbind test OK" 
# "1" "data copied"  
# "4" "data copied"  
# "0" "rbind test 2 OK"