R data.table:组的子组加权百分比

C8H*_*4O2 8 grouping r data.table

data.table喜欢:

library(data.table)
widgets <- data.table(serial_no=1:100, 
                      color=rep_len(c("red","green","blue","black"),length.out=100),
                      style=rep_len(c("round","pointy","flat"),length.out=100),
                      weight=rep_len(1:5,length.out=100) )
Run Code Online (Sandbox Code Playgroud)

虽然我不知道这是最data.table方式,我可以使用组计算群的频率tablelength在例如单step--,要回答这个问题:"是什么圆百分之红色小部件?"

编辑:此代码未提供正确答案

# example A
widgets[, list(style = unique(style), 
               style_pct_of_color_by_count = 
                 as.numeric(table(style)/length(style)) ), by=color]

#    color  style style_pct_of_color_by_count
# 1:   red  round                        0.32
# 2:   red pointy                        0.32
# 3:   red   flat                        0.36
# 4: green pointy                        0.32
# ...
Run Code Online (Sandbox Code Playgroud)

但我不能用这种方法回答诸如"按重量,红色小部件的百分比是多少?"之类的问题.我只能提出两步法:

# example B
widgets[,list(cs_weight=sum(weight)),by=list(color,style)][,list(style, style_pct_of_color_by_weight=cs_weight/sum(cs_weight)),by=color]

#    color  style style_pct_of_color_by_weight
# 1:   red  round                    0.3466667
# 2:   red pointy                    0.3466667
# 3:   red   flat                    0.3066667
# 4: green pointy                    0.3333333
# ...
Run Code Online (Sandbox Code Playgroud)

我正在寻找一个单步的B方法,如果是可以改进的A,在一个解释中加深了我对data.table副组操作语法的理解.请注意,这个问题与带有data.table的组的加权加权和不同,因为我的涉及子组并避免多个步骤.TYVM.

Fra*_*ank 12

这几乎是一步:

# A
widgets[,{
    totwt = .N
    .SD[,.(frac=.N/totwt),by=style]
},by=color]
    # color  style frac
 # 1:   red  round 0.36
 # 2:   red pointy 0.32
 # 3:   red   flat 0.32
 # 4: green pointy 0.36
 # 5: green   flat 0.32
 # 6: green  round 0.32
 # 7:  blue   flat 0.36
 # 8:  blue  round 0.32
 # 9:  blue pointy 0.32
# 10: black  round 0.36
# 11: black pointy 0.32
# 12: black   flat 0.32

# B
widgets[,{
    totwt = sum(weight)
    .SD[,.(frac=sum(weight)/totwt),by=style]
},by=color]
 #    color  style      frac
 # 1:   red  round 0.3466667
 # 2:   red pointy 0.3466667
 # 3:   red   flat 0.3066667
 # 4: green pointy 0.3333333
 # 5: green   flat 0.3200000
 # 6: green  round 0.3466667
 # 7:  blue   flat 0.3866667
 # 8:  blue  round 0.2933333
 # 9:  blue pointy 0.3200000
# 10: black  round 0.3733333
# 11: black pointy 0.3333333
# 12: black   flat 0.2933333
Run Code Online (Sandbox Code Playgroud)

工作原理:color在进入更精细的组(colorwith style)表格之前构建顶级组()的分母.


替代品.如果styles在每个内部重复color并且这仅用于显示目的,请尝试table:

# A
widgets[,
  prop.table(table(color,style),1)
]
#        style
# color   flat pointy round
#   black 0.32   0.32  0.36
#   blue  0.36   0.32  0.32
#   green 0.32   0.36  0.32
#   red   0.32   0.32  0.36

# B
widgets[,rep(1L,sum(weight)),by=.(color,style)][,
  prop.table(table(color,style),1)
]

#        style
# color        flat    pointy     round
#   black 0.2933333 0.3333333 0.3733333
#   blue  0.3866667 0.3200000 0.2933333
#   green 0.3200000 0.3333333 0.3466667
#   red   0.3066667 0.3466667 0.3466667
Run Code Online (Sandbox Code Playgroud)

对于B,这会扩展数据,以便对每个重量单位进行一次观察.对于大数据,这样的扩展将是一个坏主意(因为它需要很多内存).此外,weight必须是一个整数; 否则,它的总和将被默默地截断为一个(例如,尝试rep(1,2.5) # [1] 1 1).