考虑这样的df:
colA colB colC colD
1 1 50 100 a
2 2 51 101 b
3 3 52 102 c
4 4 53 103 d
5 5 54 104 e
6 6 55 105 f
7 7 56 106 g
8 8 57 107 h
9 9 58 108 i
10 10 59 109 j
我想转换变量“ colA”,然后计算在select()
中由mutate()
选择的变量的行总和。我正在这样做:
df %>%
mutate(colA = colA * 60,
sum = rowSums(select(., colA, colB, colC)))
这给了我错误的结果:
colA colB colC colD sum
1 60 50 100 a 151
2 120 51 101 b 154
3 180 52 102 c 157
4 240 53 103 d 160
5 300 54 104 e 163
6 360 55 105 f 166
7 420 56 106 g 169
8 480 57 107 h 172
9 540 58 108 i 175
10 600 59 109 j 178
如果我创建一个全新的变量:
df %>%
mutate(colA_mod = colA * 60,
sum = rowSums(select(., colA_mod, colB, colC)))
我得到:
错误:评估错误:位置必须在0到n之间。
但是,当我使用两个单独的mutate()
时,我得到了正确的结果:
df %>%
mutate(colA = colA * 60) %>%
mutate(sum = rowSums(select(., colA, colB, colC)))
colA colB colC colD sum
1 60 50 100 a 210
2 120 51 101 b 272
3 180 52 102 c 334
4 240 53 103 d 396
5 300 54 104 e 458
6 360 55 105 f 520
7 420 56 106 g 582
8 480 57 107 h 644
9 540 58 108 i 706
10 600 59 109 j 768
问题是,如何转换变量/创建一个新变量并在一个mutate()
中选择它?
样本数据:
df <- data.frame(colA = 1:10,
colB = 50:59,
colC = 100:109,
colD = letters[1:10])
答案 0 :(得分:1)
一种选择是分别添加colA
library(dplyr)
df %>%
mutate(colA = colA * 60,
sum = rowSums(select(., colB, colC)) + colA)
# colA colB colC colD sum
#1 60 50 100 a 210
#2 120 51 101 b 272
#3 180 52 102 c 334
#4 240 53 103 d 396
#5 300 54 104 e 458
#6 360 55 105 f 520
#7 420 56 106 g 582
#8 480 57 107 h 644
#9 540 58 108 i 706
#10 600 59 109 j 768
在使用select(., colA, colB, colC)
时,.
是原始数据帧,并且选择的列也来自原始数据帧。因此,它不具有有关colA
的更新值的信息。这就是为什么您在第二次尝试中遇到错误的相同原因
rowSums(select(., colA_mod, colB, colC))
作为colA_mod
列不属于原始数据帧(df
)。
答案 1 :(得分:1)
切换rowSums
和select
将完成任务:
df %>%
mutate(colA = colA * 60,
sum = colA + colB + colC)
如果您有NA,请先将其设为零,以便其行为与na.rm相同:
df %>%
replace(is.na(.), 0) %>%
mutate(colA = colA * 60,
sum = colA + colB + colC)
或者,这是一个允许rowSums
和一个突变的解决方案:
df %>%
mutate(sum = rowSums(select(., colA:colC) *
matrix(rep(c(60,1,1), times = 10), byrow = T, ncol = 3), na.rm = T))
输出:
colA colB colC colD sum
1 1 50 100 a 210
2 2 NA 101 b 221
3 3 52 102 c 334
4 4 53 103 d 396
5 5 54 104 e 458
6 6 55 105 f 520
7 7 56 106 g 582
8 8 57 107 h 644
9 9 58 108 i 706
10 10 59 109 j 768
答案 2 :(得分:1)
.
是发送到管道中的内容的占位符。在这种情况下,您对colA
的更改不会更新mutate
调用中管道中的内容。
您可以添加另一个管道:
df %>%
mutate(colA = colA * 60)%>%
mutate(sum = rowSums(select(., colA, colB, colC)))