2012-09-13 82 views
2

在數據幀中的行我有以下的數據幀R替換基於準則

id f1 f2 
1 a 1 3 
2 b 3 5 
3 c 4 7 

我想替換具有與行(ID = X F1> 3的所有行中,f1 = 0, F2 = 0) 所以上面將映射到

id f1 f2 
1 a 1 3 
2 b 3 5 
3 x 0 0 

但當我

replace(x,which(x$f1>3),data.frame(id = 'x',f1=0,f2=0)) 

它沒有這樣做是正確的,它給了

id f1 f2 
1 a 1 x 
2 b 3 x 
3 c 4 x 
Warning message: 
In `[<-.data.frame`(`*tmp*`, list, value = list(id = 1L, f1 = 0, : 
    provided 3 variables to replace 1 variables 

有人可以建議一種方法來做到這一點的規模?謝謝。

+0

我看不到有關'plyr'或'apply'的內容。建議您刪除這些標籤。 'replace'只將一個向量作爲第一個參數,而不是data.frame。 –

回答

10

事情是這樣的:

x[x$f1 > 3,] <- data.frame('x', 0, 0) 

應該做的伎倆!


根據@Dinin的評論,這將無法與因子id列一起使用。使用同樣的技術能像這樣工作,但:

levels(x$id) <- c(levels(x$id), 'x') 
x[x$f1 > 3,] <- data.frame('x', 0, 0) 
droplevels(x$id) 
+1

這似乎是一個未經測試的想法,因爲在'id'是一個因素的典型情況下,它會失敗。 –

+0

啊,touche!我有'options(stringsAsFactors = FALSE)',它總是讓我陷入困境。 – Justin

+0

同意迪文。這不起作用 – broccoli

1

這裏的另一種方法(考慮到@迪文的評論)

dfrm <- data.frame(id=letters[1:3], f1=c(1,3,4), f2=c(3,5,7)) 

dfrm[dfrm$f1>3, -1] <- 0 
levels(dfrm$id) <- c(levels(dfrm$id), 'x') 
dfrm[,1]<- with(dfrm, replace(id, f1==0, 'x')) ; dfrm 

    id f1 f2 
    1 a 1 3 
    2 b 3 5 
    3 x 0 0 

使用更多的數據:

set.seed(007); N <- 12 
f1 <- sample(1:9, N, replace=TRUE) 
f2 <- sample(1:9, N, replace=TRUE) 
dfrm2 <- data.frame(id=letters[1:N], f1=f1, f2=f2) 

dfrm2[dfrm2$f1>3, -1] <- 0 
levels(dfrm2$id) <- c(levels(dfrm2$id), 'x') 
dfrm2[,1]<- with(dfrm2, replace(id, f1==0, 'x')) ; dfrm2 
    id f1 f2 
1 x 0 0 
2 x 0 0 
3 c 2 5 
4 d 1 1 
5 e 3 6 
6 x 0 0 
7 x 0 0 
8 x 0 0 
9 i 2 6 
10 x 0 0 
11 k 2 9 
12 l 3 9 

我刪除了我先前的代碼,因爲它們對這個問題沒有用處。

+0

當有多個這樣的行時,它們都不會替換所有的實例。用rbind(dfrm,dfrm)嘗試一下。 –

+0

謝謝@DWin,我剛剛編輯了我的答案,它不像Justin那麼優雅,但它有效(我希望)。 –