【问题标题】:How can I convert this long format dataframe into a wide format?如何将此长格式数据帧转换为宽格式?
【发布时间】:2019-08-14 17:09:24
【问题描述】:

我在R 中使用RStudio 进行数据分析。我目前有一个dataframe,它位于long format 中。我想把它转换成wide format

dataframe (df1) 的摘录如下所示。我已将第一列转换为factor

摘录:

df1 <- read.csv("test1.csv", stringsAsFactors = FALSE, header = TRUE)

df1$Respondent <- factor(df1$Respondent)

df1

      Respondent  Question      CS             Imp     LOS  Type  Hotel
1          1       Q1       Fully Applied     High     12   SML   ABC
2          1       Q2       Optimized         Critical 12   SML   ABC

我想要一个新的dataframe(比如df2)看起来像这样:

Respondent      Q1CS           Q1Imp     Q2CS        Q2Imp     LOS   Type   Hotel
  1          Fully Applied      High    Optimized    Critical   12   SML    ABC

如何在R 中执行此操作?

附加说明:我已尝试查看 tidyr 包及其 spread() 函数,但我很难将其用于解决这个特定问题。

【问题讨论】:

  • tidyr 不能一次完成,而是要求您为要传输的每个键/值对执行此操作。有人告诉我,较新的(尚未在 CRAN 上)tidyr::pivot_* 函数将更适合更复杂的情况,您可以在 github.com/tidyverse/tidyrtidyr.tidyverse.org/dev/articles/pivot.html 上查看它们。
  • @jay.sf 这与该问题中提到的问题不同。我的有多个值可以转换为宽格式。因此,不能使用该解决方案。

标签: r tidyr


【解决方案1】:

这可以通过gather-unite-spread 方法实现

df %>%
    group_by(Respondent) %>%
    gather(k, v, CS, Imp) %>%
    unite(col, Question, k, sep = "") %>%
    spread(col, v)
#  Respondent LOS Type Hotel          Q1CS Q1Imp      Q2CS    Q2Imp
#1          1  12  SML   ABC Fully Applied  High Optimized Critical

样本数据

df <- read.table(text =
    "      Respondent  Question      CS             Imp     LOS  Type  Hotel
1          1       Q1       'Fully Applied'     High     12   SML   ABC
2          1       Q2       'Optimized'         Critical 12   SML   ABC", header = T)

【讨论】:

    【解决方案2】:

    在 data.table 中,这可以在单行中完成......

    dcast(DT, Respondent ~ Question, value.var = c("CS", "Imp"), sep = "")[DT, `:=`(LOS = i.LOS, Type = i.Type, Hotel = i.Hotel), on = "Respondent"][]
    
       Respondent          CSQ1      CSQ2 ImpQ1    ImpQ2 LOS Type Hotel
    1:          1 Fully Applied Optimized  High Critical  12  SML   ABC
    

    一步一步解释

    创建样本数据

    DT <- fread("Respondent  Question      CS             Imp     LOS  Type  Hotel
                 1  Q1       'Fully Applied'     High     12   SML   ABC
                1   Q2       'Optimized'         Critical 12   SML   ABC", quote = '\'')
    

    按问题将数据表的一部分转换为所需的格式
    colnames 可能不是您想要的...您可以随时使用 setnames() 更改它们。

    dcast(DT, Respondent ~ Question, value.var = c("CS", "Imp"), sep = "")
    #    Respondent          CSQ1      CSQ2 ImpQ1    ImpQ2
    # 1:          1 Fully Applied Optimized  High Critical
    

    然后在原始 DT 上通过引用加入,以获得您需要的其余列...

    result.from.dcast[DT, `:=`( LOS = i.LOS, Type = i.Type, Hotel = i.Hotel), on = "Respondent"]
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-10-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-10-08
      相关资源
      最近更新 更多