按多个分隔符和顺序拆分列

Split Column by multiple delimiters and order

我正在尝试分析一些日常的幻想阵容,需要将阵容列拆分为多个列,每个位置一个。

我希望分隔符是位置 ("P"、"C"、“1B”、“2B”、"SS"、“3B”、"OF" ).

我曾尝试使用 str_split 和 separate,但对如何将它们放入单独的列中然后进行排序感到有些困惑。

这是我要拆分的列:

Lineup
1B Justin Bour P José Berríos P Justin Verlander 2B Kiké Hernández OF Cody Bellinger OF Joc Pederson C Austin Barnes SS Corey Seager OF Corey Dickerson 3B Jung Ho Kang
P José Berríos OF Albert Almora Jr. SS Javier Báez 3B Kris Bryant 2B Ben Zobrist 1B Anthony Rizzo OF Cody Bellinger OF Joc Pederson C Austin Barnes P Eric Lauer

我希望它看起来像:

P             | P                 | C               | 1B              | 2B .. and so on...
------------- | ----------------- | --------------- | --------------- |
José Berríos  | Justin Verlander  | Austin Barnes   | Justin Bour     |
José Berríos  | Eric Lauer        | Austin Barnes   | Anthony Rizzo   |

这里有一个选项

pos <- c("P", "C", "1B", "2B", "3S", "3B", "OF", "SS")
pat <- sprintf("(%s)", paste(pos, collapse = "|"))

library(tidyverse)
unlist(str_split(Lineup, "\n")) %>%
    str_split(sprintf("((?<=(%s\b))\s|\s(?=(%s\b)))", pat, pat)) %>%
    map(~as_tibble(matrix(.x, ncol = 2, byrow = T)) %>%
        group_by(V1) %>%
        mutate(n = 1:n()) %>%
        unite(col, V1, n, sep = "_") %>%
        spread(col, V2)) %>%
    bind_rows()
## A tibble: 2 x 10
#  `1B_1`   `2B_1`   `3B_1`   C_1     OF_1    OF_2   OF_3   P_1    P_2     SS_1
#  <chr>    <chr>    <chr>    <chr>   <chr>   <chr>  <chr>  <chr>  <chr>   <chr>
#1 Justin … Kiké He… Jung Ho… Austin… Cody B… Joc P… Corey… José … Justin… Corey…
#2 Anthony… Ben Zob… Kris Br… Austin… Albert… Cody … Joc P… José … Eric L… Javie…

解释:我们先定义所有的位置(注意你忘记了"SS"作为可能位置的分隔符),然后把它们变成pat中的OR正则表达式。然后我们可以首先在 "\n" 上拆分输入字符串 Lineup(对于不同的行),然后在 pat 上拆分。剩下的是一些相当基本的 tidyverse 重塑。请注意,由于相同的位置可能会出现多次,并且根据您的设计,位置应该是列名,因此我们需要通过添加数字来 "unique-ify" 个位置。


示例数据

Lineup <-
"1B Justin Bour P José Berríos P Justin Verlander 2B Kiké Hernández OF Cody Bellinger OF Joc Pederson C Austin Barnes SS Corey Seager OF Corey Dickerson 3B Jung Ho Kang
P José Berríos OF Albert Almora Jr. SS Javier Báez 3B Kris Bryant 2B Ben Zobrist 1B Anthony Rizzo OF Cody Bellinger OF Joc Pederson C Austin Barnes P Eric Lauer"