我在R中有一个data.frame。看起来像这样(但要大得多):
df <- data.frame(A = rep(NULL, 5),
B = rep(NULL, 5),
ID = c(3,6,8,9,27))
> df
A B ID
1 NULL NULL 3
2 NULL NULL 6
3 NULL NULL 8
4 NULL NULL 9
5 NULL NULL 27
为了将相应的值写入每个单元格,我需要通过列名和ID值精确地对每个单元格进行加法(第3列)。因此,在下面的示例中,X将由column = A和ID = 8来处理。 (而不是column = A和Row = 3)
> df
A B ID
1 NULL NULL 3
2 NULL NULL 6
3 X NULL 8
4 NULL NULL 9
5 NULL NULL 27
有办法吗?
这个问题似乎很简单,但答案中有不同的方面需要考虑。
OP已询问如何替换与给定ID
值匹配的行中某列的值。
首先,您必须考虑用于替换的数据类型。因此,如果A
要包含numeric类型的数据和类型为character的B
,则可以通过以下方式创建示例数据集:
df <- data.frame(A = NA_real_,
B = NA_character_,
ID = c(3,6,8,9,27),
stringsAsFactors = FALSE)
df
A B ID 1 NA <NA> 3 2 NA <NA> 6 3 NA <NA> 8 4 NA <NA> 9 5 NA <NA> 27
str(df)
'data.frame': 5 obs. of 3 variables: $ A : num NA NA NA NA NA $ B : chr NA NA NA NA ... $ ID: num 3 6 8 9 27
这样可以避免代价高昂的类型转换。参数stringsAsFactors = FALSE
将避免因错误的因子水平而导致的错误。
如上所述,by dshkol,which(df$ID==8)
返回行号。那么,一个完整的答案是:
df[which(df$ID == 8), "A"] <- 0.7
df
A B ID 1 NA <NA> 3 2 NA <NA> 6 3 0.7 <NA> 8 4 NA <NA> 9 5 NA <NA> 27
data.table
OP已经提到生产数据框架要大得多。如果对大型数据对象有许多替换操作,则考虑使用data.table
可能是值得的,因为这些只在受影响的行中就位,即不复制整个列。这样可以节省时间和内存。
另外,语法更简洁。
library(data.table)
dt <- as.data.table(df) # creating a copy of df for illustration
# replacement in place in rows given by row number
dt[which(ID == 8), A := 0.7][]
# replacement in place in rows given by condition
dt[ID == 8, A := 0.7][]
A B ID 1: NA NA 3 2: NA NA 6 3: 0.7 NA 8 4: NA NA 9 5: NA NA 27
data.table
在data.table上设置一个键将进一步加快搜索特定的ID
,代码将变得更加简洁:
setkey(dt, ID)
dt[.(8), A := 0.7][]
输出与上面显示的相同。
如果要在一列中替换许多值,将它们存储在查找表中并在连接操作的更新中使用它可能更有效:
lookupA <- data.table(ID = c(8, 3),
new = c(0.7, 1.2))
lookupA
ID new 1: 8 0.7 2: 3 1.2
dt[lookupA, on = "ID", A := new][]
A B ID 1: 1.2 NA 3 2: NA NA 6 3: 0.7 NA 8 4: NA NA 9 5: NA NA 27