Получить сетку уникальной комбинации из вектора - PullRequest
2 голосов
/ 08 ноября 2019

Я бы хотел вернуть сетку с уникальными строками из вектора последовательности. Я ищу общее решение, чтобы я мог передать любое количество последовательностей в векторе. Я не знаю терминологию для этого, так как я могу это сделать?

Пример

num <- 3
v <- c(seq(1, num, 1))

Желаемый вывод

1 2 3
2 3 1
3 1 2

Второй и третий столбец можно переключать:

1 3 2
2 1 3
3 2 1

Я пытался манипулировать expand.grid(), но он требует сортировки и фильтрации, что кажется чрезмерным.

Ответы [ 3 ]

4 голосов
/ 08 ноября 2019

Вот одно решение (порядок столбцов отличается, но идея верна):

n = 3
sweep(replicate(n, 1:n), 2, 1:n, "+") %% n + 1

     [,1] [,2] [,3]
[1,]    3    1    2
[2,]    1    2    3
[3,]    2    3    1

Объяснение :

replicate сначала создаст матрицу, в которой каждая строкаis 1:n:

     [,1] [,2] [,3]
[1,]    1    1    1
[2,]    2    2    2
[3,]    3    3    3

Затем я использую функцию sweep для добавления 1 к столбцу 1, 2 к столбцу 2, 3 к столбцу 3:

     [,1] [,2] [,3]
[1,]    2    3    4
[2,]    3    4    5
[3,]    4    5    6

В этот момент вы можете сделать модуль по матрице, а затем добавить 1, чтобы получить нужную матрицу.

Редактировать: Если вам нужно иметь тот же порядок столбцов, что и выше, может сделать

(sweep(replicate(n, 1:n), 2, 1:n, "+") + 1) %% n + 1
4 голосов
/ 08 ноября 2019

Мы можем использовать пакет permn из combinat, который генерирует все возможные перестановки v, а затем выбрать из них num, используя head

head(as.data.frame(do.call(rbind, combinat::permn(v))), num)

#  V1 V2 V3
#1  1  2  3
#2  1  3  2
#3  3  1  2

Мы также можем использовать sample для выбора любых num строк вместо первых num строк, используя head.

, где

combinat::permn(v) #gives
#[[1]]
#[1] 1 2 3

#[[2]]
#[1] 1 3 2

#[[3]]
#[1] 3 1 2

#[[4]]
#[1] 3 2 1

#[[5]]
#[1] 2 3 1

#[[6]]
#[1] 2 1 3
2 голосов
/ 08 ноября 2019

Другая базовая опция R

t(sapply(1:length(v), function(i) rep(v, 2)[i:(i+2)]))
#     [,1] [,2] [,3]
#[1,]    1    2    3
#[2,]    2    3    1
#[3,]    3    1    2

Объяснение: Мы циклически переставляем v и сохраняем векторы как векторы столбцов в матрице.


Для общих v (длины length(v)) это становится

t(sapply(1:length(v), function(i) rep(v, 2)[i:(i + length(v) - 1)]))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...