【问题标题】:reshaping a large data frame from wide to long in R在R中将大数据框从宽改成长
【发布时间】:2014-12-04 23:48:11
【问题描述】:

我已经解决了各种reshape 问题,但不相信以前有人问过这个迭代。我正在处理一个包含 81K 行和 4188 个变量的数据框。变量 161:4188 是作为不同变量呈现的测量值。 idvar 在第 1 列中。我想重复第 1:160 列并为第 169:4188 列创建新记录。最终数据框的维度为 162 列和 326,268,000 行(81K * 4028 个变量转换为唯一记录)。

这是我尝试过的:

reshapeddf <- reshape(c, idvar = "PID", varying = c(dput(names(c[161:4188]))), v.names = "viewership", timevar = "network.show", times = c(dput(names(c[161:4188]))), direction = "long")

操作未完成。我等了将近10分钟。这是正确的方法吗?我使用的是 Windows 7、8GB RAM、i5 3.20ghz PC。在 R 中完成这个转置的最有效方法是什么? BondedDust 和 Nick 的两个答案都很聪明,但我遇到了记忆问题。有没有办法使用ff 实现此线程中的三种方法中的任何一种——reshapetidyrdo.call

在下面的示例数据中,1:4 列是我要重复的列,5:9 列是要为其创建新记录的列。

structure(list(PID = c(1003401L, 1004801L, 1007601L, 1008601L, 
1008602L, 1011901L), HHID = c(10034L, 10048L, 10076L, 10086L, 
10086L, 10119L), HH.START.DATE = structure(c(1378440000, 1362974400, 
1399521600, 1352869200, 1352869200, 1404964800), class = c("POSIXct", 
"POSIXt"), tzone = ""), VISITOR.CODE = structure(c(1L, 1L, 1L, 
1L, 1L, 1L), .Label = c("0", "L"), class = "factor"), WEIGHTED.MINUTES.VIEWED..ABC...20.20.FRI = c(0, 
0, 305892, 0, 101453, 0), WEIGHTED.MINUTES.VIEWED..ABC...BLACK.ISH = c(0, 
0, 0, 0, 127281, 0), WEIGHTED.MINUTES.VIEWED..ABC...CASTLE = c(0, 
27805, 0, 0, 0, 0), WEIGHTED.MINUTES.VIEWED..ABC...CMA.AWARDS = c(0, 
679148, 0, 0, 278460, 498972), WEIGHTED.MINUTES.VIEWED..ABC...COUNTDOWN.TO.CMA.AWARDS = c(0, 
316448, 0, 0, 0, 0)), .Names = c("PID", "HHID", "HH.START.DATE", 
"VISITOR.CODE", "WEIGHTED.MINUTES.VIEWED..ABC...20.20.FRI", "WEIGHTED.MINUTES.VIEWED..ABC...BLACK.ISH", 
"WEIGHTED.MINUTES.VIEWED..ABC...CASTLE", "WEIGHTED.MINUTES.VIEWED..ABC...CMA.AWARDS", 
"WEIGHTED.MINUTES.VIEWED..ABC...COUNTDOWN.TO.CMA.AWARDS"), row.names = c(NA, 
6L), class = "data.frame")

【问题讨论】:

  • 我可以提供您的数据样本吗?可能可以使用 data.table 包解决它
  • 请发布数据的简化版本。应该能够使用 3 个 ID 变量和 5 个或 6 个值列来做到这一点。需要知道列名是什么样的。

标签: r bigdata reshape ff


【解决方案1】:

可能就像这样简单:

   dat2 <- cbind(dat[1:4],   stack( dat[5:length(dat)] )

【讨论】:

  • 我同意名为“c”的对象。只是使用字母的坏习惯。也刚刚意识到reshape 代码适用于示例数据。只是太花时间了。您发布的do.call 的语法是否正确? (以逗号结尾等)
  • 不,不正确。我正要删除它,直到我测试了正确的版本。
  • Error: cannot allocate vector of size 2.4 Gb In addition: Warning messages: 1: In unlist(unname(x)) : Reached total allocation of 8100Mb: see help(memory.size) 2: In unlist(unname(x)) : Reached total allocation of 8100Mb: see help(memory.size) 3: In unlist(unname(x)) : Reached total allocation of 8100Mb: see help(memory.size) 4: In unlist(unname(x)) : Reached total allocation of 8100Mb: see help(memory.size)
  • 两种方法都遇到内存问题。
  • 嗯,我的问题集中在我的数据集很大这一事实上,我认为在 R 中存在处理大数据的方法,这正是我希望来自SO 上有经验丰富的 R 社区。​​span>
【解决方案2】:

我认为这应该可行:

library(tidyr)
newdf <- gather(yourdf, program, minutes, -PID:-VISITOR.CODE)

【讨论】:

  • Error: cannot allocate vector of size 1.2 Gb In addition: Warning messages: 1: In melt_dataframe(data, as.integer(id.ind - 1), as.integer(measure.ind - : Reached total allocation of 8100Mb: see help(memory.size) 2: In melt_dataframe(data, as.integer(id.ind - 1), as.integer(measure.ind - : Reached total allocation of 8100Mb: see help(memory.size) 3: In melt_dataframe(data, as.integer(id.ind - 1), as.integer(measure.ind - : Reached total allocation of 8100Mb: see help(memory.size)
  • 遇到内存问题。我在 8GB RAM 上。
  • @vagabond 也许是 data.table?我不知道,但它应该适用于更大的数据集。
猜你喜欢
  • 1970-01-01
  • 2020-08-20
  • 2018-11-18
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-04-19
相关资源
最近更新 更多