Все комбинации элементов векторов различной длины с условиями выбора только одного элемента на вектор и без учета порядка? - PullRequest
1 голос
/ 26 октября 2019

Представьте, что у нас есть три вектора:

v_1 = c("a", "b", "c", "d")
v_2 = c("e", "f", "g")
v_3 = c("h", "i")

Я хотел бы использовать R для получения полного списка всех комбинаций этих трех векторов для всех возможных длин при условии, что:

  • мы можем выбрать максимум 1 элемент на вектор (например, комбинация «ab» не должна учитываться, поскольку они оба принадлежат v_1)
  • порядок не важен (например,комбинация «ae» и «ea» должна учитываться только один раз).

Учитывая, что я правильно сделал математику, мы должны получить 59 различных комбинаций длин от 1 до 3. изучил функцию combn(), но кажется, что трудно (или невозможно?) применить два условия. У кого-нибудь есть предложения как решить это в R?

Спасибо!

Ответы [ 2 ]

1 голос
/ 26 октября 2019

Я думаю, что ваш общий подход обоснован, но его можно упростить, передав список ваших векторов непосредственно в combn() и используя expand.grid() в качестве аргумента функции. Тогда все, что вам нужно сделать, это связать вывод в фрейм данных.

v_1 = c("a", " b", "c", "d")
v_2 = c("e", "f", "g")
v_3 = c("h", "i")

library(purrr)
library(dplyr)

my_list <- list(v_1, v_2, v_3)

map(seq_along(my_list), ~combn(my_list, .x, FUN = function(x) list(expand.grid(x, stringsAsFactors = FALSE)))) %>%
  map_df(bind_rows)

   Var1 Var2 Var3
1     a <NA> <NA>
2     b <NA> <NA>
3     c <NA> <NA>
4     d <NA> <NA>
5     e <NA> <NA>
6     f <NA> <NA>
7     g <NA> <NA>
8     h <NA> <NA>
9     i <NA> <NA>
10    a    e <NA>
...
58    c    g    i
59    d    g    i
0 голосов
/ 26 октября 2019

Я добавил еще несколько мыслей к этому, и это, кажется, делает свое дело.

На первом шаге я объединил все имена векторов:

vectors = c("v_1", "v_2", "v_3")

Во-вторых, я создалСписок всех взаимоисключающих способов объединения этих трех векторов:

list_comb_vectors = do.call("c", lapply(seq_along(vectors), function(i) combn(vectors, i, FUN = list)))

В-третьих, я создал функцию, которая обрабатывает все эти комбинации, то есть от 1 до length(list_comb_vectors). Наконец, я использую функцию expand.grid():

go_through_combination <- function(v) {

i = list_comb_vectors[[v]]

list_of_vars = do.call("c", lapply(seq_along(i), function(x) paste0(i[x],"=",i[x])))
list_of_expression = paste(list_of_vars, collapse=",")

eval(parse(text = paste0('expand.grid(', list_of_expression, ')')))

}

mapped <- map_df(1:length(list_comb_vectors), go_through_combination)

Несмотря на то, что это решает проблему, я уверен, что есть более элегантное решение проблемы.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...