【问题标题】:Reshaping issues in R: my reshaped dataframe changes 3 variables into 1R 中的重塑问题:我重塑的数据框将 3 个变量变为 1 个
【发布时间】:2017-03-10 10:06:03
【问题描述】:

我是 R 的相对新手,并试图将我的数据从宽格式重塑为长格式并遇到问题。我在想我的问题可能是由于从我在 R 中创建的 data.frame 制作了 data.frame,将大 data.frame 的平均值转换为另一个 data.frame。

我所做的是这创建了一个空的 data.frame (ndf):

ndf <- data.frame(matrix(ncol = 0, nrow = 3))

然后使用 lapply 将大 data.frame (ldf) 中的平均值放入新 data.frame 中的单独列中,使用大 data.frame 中的年份:

ndf$Year <- names(ldf)
ndf$col1 <- lapply(ldf, function(i) {mean(i$col1)})
ndf$col2 <- lapply(ldf, function(i) {mean(i$col2)})
etc.

reshape2 中的 melted 函数显然不起作用,因为存在非原子“测量”列。

为了使用 reshape 基函数,我使用了代码:

reshape.ndf <- reshape(ndf, 
                    varying = list(names(ndf)[2:7]), 
                    v.names = "cover",
                    timevar = "species",
                    times = names(ndf[2:7]),
                    new.row.names = 1:1000,
                    direction = "long")

然后,我的输出基本上只是将第一行用于变量。所以我的宽 data.frame 看起来像这样(对不起,奇怪的名字):

Year Cladonia.portentosa Erica.tetralix Eriophorum.vaginatum  
1 2014               11.75             35                   55     
2 2015               15.75          25.75                   70      
3 2016               22.75              5                 37.5

而长 data.frame 看起来像这样:

Year             species cover id
1 2014 Cladonia.portentosa 11.75  1
2 2015 Cladonia.portentosa 11.75  2
3 2016 Cladonia.portentosa 11.75  3
4 2014      Erica.tetralix 35.00  1
5 2015      Erica.tetralix 35.00  2
6 2016      Erica.tetralix 35.00  3

“封面”列应将每年的值放入对应年份的单元格中。

请有人告诉我哪里出错了!?

【问题讨论】:

  • 当您的宽数据中只有 4 列时,如何使用 names(ndf[2:7])
  • 你试过tidyr::gather()吗?如果没有,请检查一下。它基本上是reshape2的继任者。
  • 42 - 我只展示了数据集的一部分,我试图减少混淆,但忘记更改代码以表示我所展示的内容。
  • @roman - 我调查了 'gather()_' 但可能不够彻底。我会再试一次并报告

标签: r reshape


【解决方案1】:

这是tidyr 中“熔化”的示例。

您将需要 tidyr,但我也喜欢 dplyr,并将其包含在此处以鼓励将其与 tidyverse 的其余部分一起使用。您会在网络上找到无穷无尽的精彩教程...

library(dplyr)
library(tidyr)

我们以 iris 为例,我想要一个长表格,其中种类、变量和值是列。

data(iris)

这里是gather()。我们指定变量和值是新“融化”列的列名。我们还指定我们不想熔化列 Species 我们希望保留它自己的列。

iris_long <- iris %>%
  gather(variable, value, -Species)

检查iris_long 对象以确保其正常工作。

【讨论】:

  • 谢谢@roman - 在您发表评论后,我实际上只是在我的数据集上尝试了 gather() 并且效果很好!我不确定我之前尝试的时候做错了什么,我可能在一天结束时匆匆忙忙。
  • 太棒了!很高兴听到它。
【解决方案2】:

除了 roman 的回答,我想我会准确地分享我对数据集所做的事情。

我最初的“宽”data.frame ndf 看起来像这样:

Year Cladonia.portentosa Erica.tetralix Eriophorum.vaginatum  
1 2014               11.75             35                   55     
2 2015               15.75          25.75                   70      
3 2016               22.75              5                 37.5

我用下载的tidyr

install.packages("tidyr")

然后选择包

library(tidyr)

然后,我使用 tidyr 包中的 gather() 函数将 speciesCladonia.portentosa Erica.tetralixEriophorum.vaginatum 合并为一列,并在新的“long”中使用 cover 列" 数据帧。

long.ndf <- ndf %>% gather(species, cover, Cladonia.portentosa:Eriophorum.vaginatum)

简单易懂! 再次感谢罗曼的建议!

【讨论】:

    【解决方案3】:

    我正在回答您的问题,以防它可以帮助使用reshape 功能的人。

    请有人告诉我哪里出错了!?

    您尚未指定参数idvar,而reshape 已为您创建了一个名为id 的参数。为了避免这种情况,只需将idvar = "Year" 行添加到您的代码中:

    ndf <- read.table(text = 
      "Year Cladonia.portentosa Erica.tetralix Eriophorum.vaginatum
        1 2014               11.75             35                   55     
        2 2015               15.75          25.75                   70      
        3 2016               22.75              5                 37.5", 
      header=TRUE, stringsAsFactors = F)
    
    reshape.ndf <- reshape(ndf, 
      varying = list(names(ndf)[2:4]), 
      v.names = "cover",
      idvar = "Year",
      timevar = "species",
      times = names(ndf[2:4]),
      new.row.names = 1:9,
      direction = "long")
    

    结果如你所愿

    reshape.ndf
      Year              species cover
    1 2014  Cladonia.portentosa 11.75
    2 2015  Cladonia.portentosa 15.75
    3 2016  Cladonia.portentosa 22.75
    4 2014       Erica.tetralix 35.00
    5 2015       Erica.tetralix 25.75
    6 2016       Erica.tetralix  5.00
    7 2014 Eriophorum.vaginatum 55.00
    8 2015 Eriophorum.vaginatum 70.00
    9 2016 Eriophorum.vaginatum 37.50
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2012-10-02
      • 1970-01-01
      • 2021-10-12
      • 2013-11-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多