我有一个如下所示的数据框,其中有很多列和数据
Label 2015-08-24 2015-08-25
1 AxG 179238.8 174160.3
2 CHaF 203544.2 199411.9
3 HHHH 130138.9 129182.2
4 fLS 146367.0 148708.0
5 KSU 194584.7 188508.0
6 MqCC 272922.7 273369.5
7 BEPU 0.0 0.0
8 SSEX 107566.4 111552.8
9 QQQ 248380.4 257064.2
10 AAA 258735.4 260415.5
我有另一个数据框,其行索引与第一个中的列名相同(在本例中为日期)。我想将第一个数据帧的列中的每个值除以第二个
中的相应值 totals
2015-08-24 1741479
2015-08-25 199411.9
我的第一个想法是做下面的事情(我来自pythonic背景,虽然不久前)
> for(i in names(df1)){
+ df1[[df1[,i]/df2[i,]]]
但这是我收到的错误:
.subset2(x,i,exact = exact)中的错误:在1级In中没有这样的索引 另外:警告信息:在Ops.factor(权重[,i], weight_totals [i,]):'/'对因子无意义
有什么想法吗?
答案 0 :(得分:5)
我们也可以使用sweep
。对于必须在数组上应用值向量的任何情况,它都是一个有用的函数。我们选择保证金2
来扫描列(我们可以为行选择1
):
sweep(df[-1], 2, df2$totals, '/')
# 2015-08-24 2015-08-25
# [1,] 0.10292332 0.8733696
# [2,] 0.11688008 1.0000000
# [3,] 0.07472895 0.6478159
# [4,] 0.08404753 0.7457328
# [5,] 0.11173531 0.9453197
# [6,] 0.15671892 1.3708786
# [7,] 0.00000000 0.0000000
# [8,] 0.06176727 0.5594089
# [9,] 0.14262612 1.2891116
# [10,] 0.14857222 1.3059176
答案 1 :(得分:4)
您可以转置第二个data.frame
并使用intersect()
dft <- data.frame(t(df2), check.names = FALSE) # transpose df2
mapply("/", df[intersect(names(df), names(dft))],
dft[intersect(names(df), names(dft))]) # perfrom division
# 2015-08-24 2015-08-25
# [1,] 0.10292332 0.8733696
# [2,] 0.11688008 1.0000000
# [3,] 0.07472895 0.6478159
# [4,] 0.08404753 0.7457328
# [5,] 0.11173531 0.9453197
# [6,] 0.15671892 1.3708786
# [7,] 0.00000000 0.0000000
# [8,] 0.06176727 0.5594089
# [9,] 0.14262612 1.2891116
#[10,] 0.14857222 1.3059176
使用的数据:
df <- structure(list(Label = structure(c(2L, 4L, 6L, 5L, 7L, 8L, 3L,
10L, 9L, 1L), .Label = c("AAA", "AxG", "BEPU", "CHaF", "fLS",
"HHHH", "KSU", "MqCC", "QQQ", "SSEX"), class = "factor"), `2015-08-24` = c(179238.8,
203544.2, 130138.9, 146367, 194584.7, 272922.7, 0, 107566.4,
248380.4, 258735.4), `2015-08-25` = c(174160.3, 199411.9, 129182.2,
148708, 188508, 273369.5, 0, 111552.8, 257064.2, 260415.5)), .Names = c("Label",
"2015-08-24", "2015-08-25"), class = "data.frame", row.names = c("1",
"2", "3", "4", "5", "6", "7", "8", "9", "10"))
df2 <- structure(list(totals = c(1741479, 199411.9)), .Names = "totals", row.names = c("2015-08-24",
"2015-08-25"), class = "data.frame")
答案 2 :(得分:2)
Altough @PierreLafortune具有最短的解决方案,使用sweep
要求df
的列名称和df2
的rownames的顺序必须相同。使用for
时(我还想使用@mtoto的intersect
方法),df
的列名和df2
的rownames不必位于获得所需结果的顺序相同。另一个优点是df
立即更新:
for(i in names(df)[-1])
df[, i] <- df[, i] / df2$totals[match(i, row.names(df2))]
给出:
> df
Label 2015-08-24 2015-08-25
1 AxG 0.10292332 0.8733696
2 CHaF 0.11688008 1.0000000
3 HHHH 0.07472895 0.6478159
4 fLS 0.08404753 0.7457328
5 KSU 0.11173531 0.9453197
6 MqCC 0.15671892 1.3708786
7 BEPU 0.00000000 0.0000000
8 SSEX 0.06176727 0.5594089
9 QQQ 0.14262612 1.2891116
10 AAA 0.14857222 1.3059176