如何分隔包含有序对列表的列?

How to separate a column that contains a lists of ordered pairs?

我有一个数据集 df,其中第三列 new 的形式为

我想问一下如何从 new 创建 2 个新列,其中第一列包含每个列表中的第一个元素,第二列包含每个列表中的第二个元素。特别是,它看起来像

这可以通过遍历每一行的简单循环来完成。因为我的真实数据集包含超过 100.000 行,所以循环效率不高。能否请您详细说明一个有效的方法?

data("mtcars")
df <- mtcars[, 1:2]
df$new <- lapply(setNames(asplit(df[c('mpg', 'cyl')], 1), NULL), as.vector)
df$mpg <- 0
df$cyl <- 0

因为它是 vectorlist,我们可以用 do.callrbind 它们,并用 setNames[= 改变列名17=]

out <- setNames(do.call(rbind.data.frame, df$new), c('var1', 'var2'))

如果需要分配给'mpg','cyl'已经创建为'0'

df[c('mpg', 'cyl')] <- do.call(rbind, df$new)

这里是 data.table 选项,使用 transpose

setDT(df)[, setNames(transpose(new), c("mpg", "cyl"))]

这给出了

    mpg cyl
 1:   21   6
 2:   21   6
 3: 22.8   4
 4: 21.4   6
 5: 18.7   8
 6: 18.1   6
 7: 14.3   8
 8: 24.4   4
 9: 22.8   4
10: 19.2   6
11: 17.8   6
12: 16.4   8
13: 17.3   8
14: 15.2   8
15: 10.4   8
16: 10.4   8
17: 14.7   8
18: 32.4   4
19: 30.4   4
20: 33.9   4
21: 21.5   4
22: 15.5   8
23: 15.2   8
24: 13.3   8
25: 19.2   8
26: 27.3   4
27:   26   4
28: 30.4   4
29: 15.8   8
30: 19.7   6
31:   15   8
32: 21.4   4
     mpg cyl

> setDT(df)[, c("mpg", "cyl") := (lapply(transpose(new), unlist))][]
     mpg cyl       new
 1: 21.0   6     21, 6
 2: 21.0   6     21, 6
 3: 22.8   4 22.8, 4.0
 4: 21.4   6 21.4, 6.0
 5: 18.7   8 18.7, 8.0
 6: 18.1   6 18.1, 6.0
 7: 14.3   8 14.3, 8.0
 8: 24.4   4 24.4, 4.0
 9: 22.8   4 22.8, 4.0
10: 19.2   6 19.2, 6.0
11: 17.8   6 17.8, 6.0
12: 16.4   8 16.4, 8.0
13: 17.3   8 17.3, 8.0
14: 15.2   8 15.2, 8.0
15: 10.4   8 10.4, 8.0
16: 10.4   8 10.4, 8.0
17: 14.7   8 14.7, 8.0
18: 32.4   4 32.4, 4.0
19: 30.4   4 30.4, 4.0
20: 33.9   4 33.9, 4.0
21: 21.5   4 21.5, 4.0
22: 15.5   8 15.5, 8.0
23: 15.2   8 15.2, 8.0
24: 13.3   8 13.3, 8.0
25: 19.2   8 19.2, 8.0
26: 27.3   4 27.3, 4.0
27: 26.0   4     26, 4
28: 30.4   4 30.4, 4.0
29: 15.8   8 15.8, 8.0
30: 19.7   6 19.7, 6.0
31: 15.0   8     15, 8
32: 21.4   4 21.4, 4.0
     mpg cyl       new

一个简单的 dplyr/tidyr 替代方案可以是

library(tidyverse)

unnest_wider(df, new)

# A tibble: 32 x 4
     mpg   cyl  ...1  ...2
   <dbl> <dbl> <dbl> <dbl>
 1     0     0  21       6
 2     0     0  21       6
 3     0     0  22.8     4
 4     0     0  21.4     6
 5     0     0  18.7     8
 6     0     0  18.1     6
 7     0     0  14.3     8
 8     0     0  24.4     4
 9     0     0  22.8     4
10     0     0  19.2     6
# ... with 22 more rows