[英]Conditional dataframe mutations in R with magrittr and dplyr
我想使用magrittr和dplyr的簡潔性來根據其他列中的值在列的子集中的行之間復制單個值。 這是一個簡單的例子; 我想將這個想法應用於長數據管道中具有多個條件的大型數據集的許多列。
取數據幀df <- data.frame(a = 1:5, b = 6:10, x = 11:15, y = 16:20)
: df <- data.frame(a = 1:5, b = 6:10, x = 11:15, y = 16:20)
:
a b x y
1 6 11 16
2 7 12 17
3 8 13 18
4 9 14 19
5 10 15 20
對於a = 5
的行,我想將x
和y
的值替換為b = 7
的行中的值,以給出:
a b x y
1 6 11 16
2 7 12 17
3 8 13 18
4 9 14 19
5 10 12 17
此嘗試失敗:
foo <- function(x){ifelse(df$a == 5, df[df$b == 7, .(df$x)], x)}
df %<>% mutate_each(funs(foo), x, y)
我能得到的最接近的是:
bar <- function(x){ifelse(df$a == 5, df[df$b == 7, "x"], x)}
df %<>% mutate_each(funs(bar), x, y)
但這是不正確的,因為它將兩個值替換為x
的值,而不是x
和y
。
感謝您的建議。
您可以使用mutate_each
並replace
:
df %>% mutate_each(funs(replace(., a==5, nth(., which(b==7)))), x, y)
輸出:
a b x y
1 1 6 11 16
2 2 7 12 17
3 3 8 13 18
4 4 9 14 19
5 5 10 12 17
或者根據@docendodiscimus的評論,它可以進一步縮短(並且可能[
也比which
更好]:
df %>% mutate_each(funs(replace(., a==5, .[b==7])), x, y)
data.table
解決方案將是:
require(data.table)
setDT(df)[a == 5, c("x", "y") := df[b == 7, .SD, .SDcols = c("x", "y")]]
> df
a b x y
1: 1 6 11 16
2: 2 7 12 17
3: 3 8 13 18
4: 4 9 14 19
5: 5 10 12 17
或者,您也可以使用:
cols <- c("x", "y")
setDT(df)[a == 5, (cols) := df[b == 7, .SD, .SDcols = cols]]
# or
cols <- c("x", "y")
setDT(df)[a == 5, (cols) := df[b == 7, cols, with = FALSE]]
如果您的主要要求是在較長的dplyr-pipe中應用該函數,則可以執行類似以下示例的操作:
foo <- function(df, cols = c("x", "y")) {
df[df$a == 5, cols] <- df[df$b == 7, cols]
df
}
df %>% ... %>% foo(c("x", "y")) %>% ...
# a b x y
#1 1 6 11 16
#2 2 7 12 17
#3 3 8 13 18
#4 4 9 14 19
#5 5 10 12 17
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.