Digamos que temos uma matriz 5x5, preenchida com 0s.
myMatrix <- matrix(rep(0, 25), ncol = 5)
Agora, vamos escolher um trio de números inteiros entre 1 e 5.
triplet <- c(1,2,3)
Para todas as combinações desse trio, agora adicionamos 1 na matriz, com esta função:
addCombinationsToMatrix <- function(.matrix, .triplet){
indexesToChange <- as.matrix(expand.grid(.triplet, .triplet))
.matrix[indexesToChange] <- .matrix[indexesToChange] + 1
.matrix
}
Usando a função, passamos de
myMatrix
[,1] [,2] [,3] [,4] [,5]
[1,] 0 0 0 0 0
[2,] 0 0 0 0 0
[3,] 0 0 0 0 0
[4,] 0 0 0 0 0
[5,] 0 0 0 0 0
para
myMatrix <- addCombinationsToMatrix(myMatrix, triplet)
myMatrix
[,1] [,2] [,3] [,4] [,5]
[1,] 1 1 1 0 0
[2,] 1 1 1 0 0
[3,] 1 1 1 0 0
[4,] 0 0 0 0 0
[5,] 0 0 0 0 0
Se escolhermos outro trigêmeo, passaremos para
nextTriplet <- 2:4
myMatrix <- addCombinationsToMatrix(myMatrix, nextTriplet)
myMatrix
[,1] [,2] [,3] [,4] [,5]
[1,] 1 1 1 0 0
[2,] 1 2 2 1 0
[3,] 1 2 2 1 0
[4,] 0 1 1 1 0
[5,] 0 0 0 0 0
Portanto, combinações de linhas e colunas representam a frequência com que dois números inteiros foram mostrados juntos em um trigêmeo: 3 e 4 foram mostrados juntos uma vez, 2 e 3 foram mostrados juntos duas vezes.
Pergunta : Como se pode escolher trigêmeos, de modo que todas as combinações (1-2, 1-3, 1-4 ...) foram escolhidas pelo menos uma vez e o número de trigêmeos é minimizado.
Estou procurando um algoritmo aqui que escolhe o próximo trigêmeo.
Idealmente, pode ser estendido para
- matrizes arbitrariamente grandes (10x10, 100x100 ...)
- vetores arbitrariamente grandes (quadrupletos, quintupletos, n-tupletos)
- um número arbitrário de vezes que uma combinação deve ter sido escolhida pelo menos
Exemplo:
myMatrix
myMatrix <- addCombinationsToMatrix(myMatrix, 1:3)
myMatrix
myMatrix <- addCombinationsToMatrix(myMatrix, 3:5)
myMatrix
myMatrix <- addCombinationsToMatrix(myMatrix, c(1,4,5))
myMatrix
myMatrix <- addCombinationsToMatrix(myMatrix, c(2,4,5))
myMatrix
EDIT : Apenas para ter certeza: a resposta não precisa ser R
código. Pode ser também algum outro idioma ou mesmo pseudo-código.
EDIÇÃO 2 : Ocorreu-me agora que existem diferentes maneiras de medir a eficiência. Na verdade, eu quis dizer que o algoritmo deve ter o mínimo de iterações possível. O algoritmo que é rápido também é muito legal, mas não é o objetivo principal aqui.
fonte
Aqui está uma opção usada
data.table
para acompanhar a contagem de matrizes eRcppAlgos
gerar as combinações:É um algoritmo ganancioso, portanto, não tenho certeza se isso resultará em um número mínimo de tuplas.
fonte
Error in eval(onsub, parent.frame(2L), parent.frame(2L)) : object '.NATURAL' not found
Como essa pergunta solicita abordagens algorítmicas para cobrir projetos, fornecerei uma que forneça respostas exatas (também conhecidas como o melhor design possível) usando a programação inteira em R. desde que você esteja selecionando trigêmeos), defina uma variável de decisão que aceite o valor 1 se você a incluir em seu design e 0 se não. Portanto, no seu caso, você definiria x_123 para indicar se a tupla (1,2,3) está selecionada, x_345 para (3,4,5) e assim por diante.
O objetivo do modelo de otimização é minimizar o número de tuplas selecionadas, ou seja, a soma de todas as suas variáveis de decisão. No entanto, para cada tupla t (t = 2 no seu caso), você precisa incluir uma variável de decisão que contenha essa tupla. Isso gera uma restrição para cada tupla t. Como exemplo, teríamos
x_123+x_124+x_125 >= 1
a restrição que exige que o par12
esteja em alguma tupla selecionada.Isso produz o seguinte modelo de otimização:
Você pode estender isso para exigir repetições r de cada tupla t, alterando o lado direito de todas as desigualdades para "r" e exigindo que todas as variáveis sejam inteiras em vez de binárias.
Isso é fácil de resolver com um pacote como
lpSolve
no R:Embora isso resolva seu problema exatamente, ele não será bem dimensionado para tamanhos de problemas grandes. Isso ocorre porque o problema é difícil para o NP - nenhum algoritmo exato conhecido será dimensionado bem. Se você precisar solucionar grandes instâncias de problemas, as heurísticas recomendadas em outras respostas aqui são sua melhor aposta. Ou você pode resolver com programação inteira (como fazemos aqui) e definir um tempo limite; você estará trabalhando com a melhor solução encontrada pelo tempo limite, que é uma solução heurística para o problema em geral.
fonte