首页 > 解决方案 > R代码将单列(每条记录的长度可变)中的数据拆分为列

问题描述

我在单个 Excel 列中有数据,因此:

123456
$200 
Bidder A
$300 
Bidder B
$320 
Bidder C
~
987654
$12 
Bidder X
$15 
Bidder Y
$20 
~
…

第一个记录包含 3 个投标,第二个记录只有 2 个投标。每条记录最多可以有 40 个出价或每条记录只有 1 个出价,因此每条记录的行数会有所不同。“~”是“新记录”的分隔符。

我想将此(最好在 R 中)转换为这种格式:

123456  Bidder A    $200    Bidder B    $300    Bidder C    $320    … <up to 40 bids & amounts>
987654  Bidder X    $12     Bidder X    $15     Bidder Y    NULL    … <up to 40 bids & amounts> 
...
...

ETC

我可以很容易地将它从 CSV 读入 R,但非常感谢帮助以优雅的方式更改表单。我的直觉是建议这样做很长的路要走(编写一些代码,以继续逐行读取列并放入列中,直到达到我的“〜”分隔符,然后开始新的一行)但我正在尝试抵制并学习 R :-)

如果在 R 之外更容易完成(也许在 Excel 本身中,也可以),但是一旦它的 Tidy 数据,我将使用 R 来操作。

提前致谢 :-)

劳伦斯

标签: rtidyverse

解决方案


考虑这个函数

parse_records <- function(x, delim = "~") {
  delim <- x == delim
  id <- cumsum(delim)
  rows <- split(x[!delim], id[!delim])
  dr <- max(lengths(rows))
  out <- as.data.frame(t(vapply(rows, `[`, character(dr), seq_len(dr))))
  row.names(out) <- NULL
  out
}

然后你可以

> parse_records(x)
      V1   V2       V3   V4       V5   V6       V7   V8
1 123456 $200 Bidder A $300 Bidder B $320 Bidder C <NA>
2 987654  $12 Bidder X  $15 Bidder Y  $20     <NA> <NA>
3 135678 $123 Bidder E $234 Bidder F $393 Bidder G $222

关键假设是您的数据是这样的字符向量

> x
 [1] "123456"   "$200"     "Bidder A" "$300"     "Bidder B" "$320"     "Bidder C" "~"        "987654"   "$12"      "Bidder X" "$15"      "Bidder Y"
[14] "$20"      "~"        "135678"   "$123"     "Bidder E" "$234"     "Bidder F" "$393"     "Bidder G" "$222" 

数据

c("123456", "$200", "Bidder A", "$300", "Bidder B", "$320", "Bidder C", 
"~", "987654", "$12", "Bidder X", "$15", "Bidder Y", "$20", "~", 
"135678", "$123", "Bidder E", "$234", "Bidder F", "$393", "Bidder G", 
"$222")

推荐阅读