我有dataframe
列A,B和C.
我想在dataframe
的每一行上应用一个函数,其中函数将检查row$A
和row$B
的值,并根据这些值更新row$C
。我怎样才能做到这一点?
示例:
A B C
1 1 10 10
2 2 20 20
3 NA 30 30
4 NA 40 40
5 5 50 50
现在,如果该行的A列中的值为NA
,我想将C列中的所有行更新为同一行中的B / 2值。
因此,更改后的dataframe
将如下所示:
A B C
1 1 10 10
2 2 20 20
3 NA 30 15
4 NA 40 20
5 5 50 50
我想知道是否可以在不使用for
循环的情况下完成此操作。
答案 0 :(得分:2)
或者,如果您想通过引用更新列(在更新列时不复制整个数据集)也可以尝试data.table
library(data.table)
setDT(dat)[is.na(A), C := B/2]
dat
# A B C
# 1: 1 10 10
# 2: 2 20 20
# 3: NA 30 15
# 4: NA 40 20
# 5: 5 50 50
编辑: 关于@aruns注释,在更改之前和之后检查地址意味着它仍然通过引用更新。
library(pryr)
address(dat$C)
## [1] "0x2f85a4f0"
setDT(dat)[is.na(A), C := B/2]
address(dat$C)
## [1] "0x2f85a4f0"
答案 1 :(得分:1)
试试这个:
your_data <- within(your_data, C[is.na(A)] <- B[is.na(A)] / 2)
答案 2 :(得分:0)
尝试
indx <- is.na(df$A)
df$C[indx] <- df$B[indx]/2
df
# A B C
#1 1 10 10
#2 2 20 20
#3 NA 30 15
#4 NA 40 20
#5 5 50 50
答案 3 :(得分:0)
这是使用library(dplyr)
的简单示例。
虚构数据集:
df <- data.frame(a=c(1, NA, NA, 2), b=c(10, 20, 50, 50))
你只想要那些a == NA的行,因此你可以使用ifelse
:
df <- mutate(df, c=ifelse(is.na(a), b/2, b))
答案 4 :(得分:0)
另一种方法:
dat <- transform(dat, C = B / 2 * (i <- is.na(A)) + C * !i)
# A B C
# 1 1 10 10
# 2 2 20 20
# 3 NA 30 15
# 4 NA 40 20
# 5 5 50 50
答案 5 :(得分:0)
尝试:
> ddf$C = with(ddf, ifelse(is.na(A), B/2, C))
>
> ddf
A B C
1 1 10 10
2 2 20 20
3 NA 30 15
4 NA 40 20
5 5 50 50