【发布时间】:2017-02-09 19:05:26
【问题描述】:
我有以下数据框
dat <- data.frame(x=c(1,2,3,3,2,1), y=c(3,4,4,5,2,5))
现在我想得到第三列,将 y 行值除以聚合 y 值(基于 x 列中的唯一值)。所以,然后我得到如下第 1 行:1,3,0.375; 0.375 计算为 3 / (5+3)。
我对 R 比较陌生,希望你能帮助我。谢谢!
【问题讨论】:
标签: r
我有以下数据框
dat <- data.frame(x=c(1,2,3,3,2,1), y=c(3,4,4,5,2,5))
现在我想得到第三列,将 y 行值除以聚合 y 值(基于 x 列中的唯一值)。所以,然后我得到如下第 1 行:1,3,0.375; 0.375 计算为 3 / (5+3)。
我对 R 比较陌生,希望你能帮助我。谢谢!
【问题讨论】:
标签: r
解决这个问题的方法有很多种,这里有一个
with(dat, ave(y, x, FUN = function(x) x/sum(x)))
## [1] 0.3750000 0.6666667 0.4444444 0.5555556 0.3333333 0.6250000
这是另一种可能性
library(data.table)
setDT(dat)[, z := y/sum(y), by = x]
dat
# x y z
# 1: 1 3 0.3750000
# 2: 2 4 0.6666667
# 3: 3 4 0.4444444
# 4: 3 5 0.5555556
# 5: 2 2 0.3333333
# 6: 1 5 0.6250000
这是第三个
library(dplyr)
dat %>%
group_by(x) %>%
mutate(z = y/sum(y))
# Source: local data frame [6 x 3]
# Groups: x
#
# x y z
# 1 1 3 0.3750000
# 2 2 4 0.6666667
# 3 3 4 0.4444444
# 4 3 5 0.5555556
# 5 2 2 0.3333333
# 6 1 5 0.6250000
【讨论】:
with(dat,y/ ave(y,x, FUN=sum)) 会更紧凑一些。另一种选择dat$y/xtabs(y~x, dat)[dat$x]
dplyr 中,sum 对之前的group_by 创建的组求和。试试dat <- data.frame(x=c(1,1,4,4,5,5,6,6), y=c(5,6,1,0,3,1,2,3)) 然后dat %>% group_by(x) %>% group_by(y) %>% mutate(w = y/sum(x)) 看看group_by(x) 没有效果。相反,不分组将整个数据框视为组:dat %>% mutate(w = y/sum(x)) 计算相对权重总和为 1。或者dat %>% mutate(rel_x = x/sum(x)) %>% summarize(total = sum(rel_x)) 应为 1。
以下是一些基本的 R 解决方案:
1) prop.table 像这样使用prop.table 基函数和ave:
transform(dat, z = ave(y, x, FUN = prop.table))
给予:
x y z
1 1 3 0.3750000
2 2 4 0.6666667
3 3 4 0.4444444
4 3 5 0.5555556
5 2 2 0.3333333
6 1 5 0.6250000
2) sum 这也有效:
transform(dat, z = y / ave(y, x, FUN = sum))
【讨论】:
当然还有一种方法可以让人们用 SQL 来思考,在这种情况下非常罗嗦,但很好地概括了各种其他类似的问题:
library(sqldf)
dat <- sqldf("
with sums as (
select
x
,sum(y) as sy
from dat
group by x
)
select
d.x
,d.y
,d.y/s.sy as z
from dat d
inner join sums s
on d.x = s.x
")
【讨论】: