【问题标题】:Compute quantiles incorporating Sample Design (Survey package)计算包含样本设计的分位数(调查包)
【发布时间】:2015-11-16 23:54:57
【问题描述】:

我想使用包含复杂调查样本设计的另一列(连续变量)的分位数来计算新列。这个想法是在数据框中创建一个新变量,该变量指示每个观察值属于哪个分位数组

这是我在不包含示例设计的情况下执行该想法的方式,因此您可以了解我的目标。

# Load Data
  data(api)


# Convert data to data.table format (mostly to increase speed of the process)
  apiclus1 <- as.data.table(apiclus1)

# Create deciles variable
apiclus1[, decile:=cut(api00,
                       breaks=quantile(api00,
                                       probs=seq(0, 1, by=0.1), na.rm=T),
                       include.lowest= TRUE, labels=1:10)]

我尝试使用 survey 包中的 svyquantile,但我无法解决这个问题。此代码不会将分位数组作为我可以输入新变量的输出返回。对此有什么想法吗?

# Load Package
 library(survey)

# create survey design
 dclus1 <- svydesign(id=~dnum, weights=~pw, data=apiclus1, fpc=~fpc)

# What I've tried to do
  svyquantile(~api00, design = dclus1, quantiles = seq(0, 1, by=0.1), method = "linear", ties="rounded")

【问题讨论】:

    标签: r survey quantile


    【解决方案1】:
    library(survey)
    
    data(api)
    
    dclus1 <- svydesign(id=~dnum, weights=~pw, data=apiclus1, fpc=~fpc)
    
    a <- svyquantile(~api00, design = dclus1, quantiles = seq(0, 1, by=0.1), method = "linear", ties="rounded")
    
    # use factor() and findInterval()
    dclus1 <- update( dclus1 , qtile = factor( findInterval( api00 , a ) ) )
    
    # distribution
    svymean( ~ qtile , dclus1 )
    
    
    # or without the one observation in group number 11
    dclus1 <- update( dclus1 , qtile = factor( findInterval( api00 , a[ -length( a ) ] ) ) )
    
    # distribution
    svymean( ~ qtile , dclus1 )
    
    
    
    # quantiles by group
    b <- svyby(~api00, ~stype, design = dclus1, svyquantile, quantiles = seq(0, 0.9 , by=0.1) ,ci=T)
    
    # copy over your data
    x <- apiclus1
    
    # stype of each record
    match( x$stype , b$stype ) 
    
    # create the new qtile variable
    x$qtile_by_stype <- factor( diag( apply( data.frame( b )[ match( x$stype , b$stype ) , 2:11 ] , 1 , function( v , w ) findInterval( w , v ) , x$api00 ) ) )
    
    # re-create the survey design
    dclus1 <- svydesign(id=~dnum, weights=~pw, data=x, fpc=~fpc)
    
    # confirm you have quantiles
    svyby( ~ qtile_by_stype , ~ stype , dclus1 , svymean )
    

    【讨论】:

    • 感谢@Anthony。关于如何按子组执行此操作的任何想法?对于提取分位数的第一部分,我认为使用这个b &lt;- svyby(~api00, ~stype, design = dclus1, svyquantile, quantiles = seq(0, 1, by=0.1), method = "linear", ties="rounded", na.rm= T, ci=TRUE) 但我承认我不知道如何使用这个对象b 来更新调查设计或数据集中的值
    • @RafaelPereira 有点丑,但肯定有可能......注意2:11 已被硬编码。查看data.frame(b) 以检查为什么选择这些列用于此特定示例
    • 在你的代码中按组计算十分位数,你为什么写seq(0, 0.9 , by=0.1),而不是seq(0, 10 , by=0.1)
    【解决方案2】:

    上面整个代码的输出是:

            0   0.1   0.2   0.3   0.4    0.5   0.6    0.7   0.8   0.9   1
    api00 411 497.8 535.6 573.2 614.6 651.75 686.6 709.55 735.4 780.7 905
    

    您可以更改名称以代表您的组。 0 和 1 代表最小值和最大值。 0.1 代表十分位 1,0.2 代表十分位 2,等等。类似于:

    dt_quantile = svyquantile(~api00, design = dclus1, quantiles = seq(0, 1, by=0.1), method = "linear", ties="rounded")
    dt_quantile = data.table(dt_quantile)
    
    setnames(dt_quantile, c("min",paste0("decile",1:10)))
    
    dt_quantile = data.table(t(dt_quantile), keep.rownames = T)
    
    dt_quantile 
    
    #         rn     V1
    # 1:      min 411.00
    # 2:  decile1 497.80
    # 3:  decile2 535.60
    # 4:  decile3 573.20
    # 5:  decile4 614.60
    # 6:  decile5 651.75
    # 7:  decile6 686.60
    # 8:  decile7 709.55
    # 9:  decile8 735.40
    # 10: decile9 780.70
    # 11: decile10 905.00
    

    我错过了你的目标吗?

    【讨论】:

    • 谢谢@AntoniosK,但这个想法实际上是在数据框中创建一个新变量,指示每个观察值属于哪个分位数组。
    • 你是对的。我认为它只是计算分位数,而没有加入每行所属的分位数的信息。这就是函数的用途。但是,您在 dclus1$variables 中有信息,您可以将其用作数据集并应用您的方法。
    猜你喜欢
    • 2020-01-05
    • 1970-01-01
    • 2018-09-03
    • 1970-01-01
    • 1970-01-01
    • 2023-03-18
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多