Considere uma matriz de números inteiros:
[1, 0, 9, 1, 3, 8]
Existem várias maneiras de particionar esta lista em sublistas consecutivas. Aqui estão três:
A: [[1, 0, 9], [1, 3, 8]]
B: [[1], [0, 9], [1, 3], [8]]
C: [[1, 0], [9, 1], [3, 8]]
Chamaremos uma partição Y e o refinamento de outra partição X se X puder ser obtido de Y juntando algumas de suas sublistas novamente.
O mesmo B
vale para um refinamento de A
: se juntarmos os dois primeiros e os dois últimos sublistas juntos, obteremos A
. Mas C
é não um refinamento A
: teríamos que dividir o 9
e 1
a fim de recuperar A
a partir dele. Além disso, qualquer partição é trivialmente um refinamento de si mesma.
Observe que não temos permissão para reorganizar sublistas ou elementos a qualquer momento.
O desafio
Dadas duas partições (listas de listas de números inteiros) X
e Y
, determine se Y
é um refinamento de X
.
Você pode assumir que as partições conterão apenas números inteiros de 0
até 9
, inclusive. Você não deve assumir isso X
e Y
é partição da mesma lista (se não for, também não será um refinamento um do outro). X
e / ou Y
pode estar vazio, mas nunca conterá sublistas vazias.
Você pode escrever um programa ou função, recebendo entrada via STDIN (ou alternativa mais próxima), argumento da linha de comando ou argumento da função e emitindo o resultado via STDOUT (ou alternativa mais próxima), valor de retorno da função ou parâmetro da função (saída).
A entrada pode ser obtida em qualquer formato conveniente de sequência ou lista. Como os elementos serão apenas números inteiros de um dígito, você pode optar por omitir um delimitador nas sublistas, mas certifique-se de que 0
s iniciais sejam possíveis. Você pode optar por tomar X
e Y
em ordem oposta.
A saída deve ser verdadeira se Y
for um refinamento X
e uma falsificação de outra forma.
Seu código deve ser capaz de resolver cada um dos casos de teste abaixo em 1 segundo em uma máquina de desktop razoável. (Esta é apenas uma verificação de sanidade para evitar soluções simples de força bruta.)
Isso é código de golfe, então a resposta mais curta (em bytes) vence.
Casos de teste
Cada caso de teste está em sua própria linha, escrita como X Y
. Estou usando a notação de matriz no estilo GolfScript / CJam para economizar espaço horizontal:
Verdade:
[] []
[[0]] [[0]]
[[1 0 9 1 3 8]] [[1 0 9] [1 3 8]]
[[1 0 9 1 3 8]] [[1 0 9 1 3] [8]]
[[1 0 9 1 3 8]] [[1] [0] [9] [1] [3] [8]]
[[1 0 9] [1 3 8]] [[1 0 9] [1 3 8]]
[[1 0 9] [1 3 8]] [[1] [0 9] [1 3] [8]]
[[9 8 8 5 8 2 7] [5] [1 4] [2 0 0 6 0 8 4 2 6 4 2 3 7 8 7 3 9 5 7 9 8 2 9 5] [3 9 8] [7 1 4 9 7 4 5 9] [3 3 3] [9 0 7 8] [3 9 4 7 2 7 8 0 3 0] [8 2 2 7 3 9 3 2] [2 9 0 8 5 4 1 8 5 5 6 2 0 9 2 7 7 9 2 7] [3 6] [1 2 7 7 4 4 2 9]] [[9 8] [8] [5 8 2] [7] [5] [1 4] [2] [0 0 6] [0] [8 4 2] [6 4] [2] [3] [7 8] [7 3] [9] [5 7 9] [8 2] [9 5] [3] [9 8] [7 1 4] [9 7] [4 5 9] [3 3] [3] [9 0] [7 8] [3] [9] [4] [7 2] [7 8] [0] [3 0] [8 2] [2] [7 3] [9 3] [2] [2] [9] [0] [8 5 4] [1 8] [5 5] [6] [2 0] [9] [2] [7 7 9] [2 7] [3 6] [1 2] [7 7] [4 4 2] [9]]
Falsy:
[[0]] []
[[0]] [[1]]
[[1 0 9]] [[1 0 9] [1 3 8]]
[[1 0 9] [1 3 8]] [[1 0 9 1 3 8]]
[[1 0 9] [1 3 8]] [[1 0 9]]
[[1 0 9] [1 3 8]] [[1 0] [9]]
[[1 0 9] [1 3 8]] [[1 0] [9 1] [3 8]]
[[1] [0 9] [1 3] [8]] [[1 0 9] [1 3 8]]
[[9 8 8 5 8 2 7] [5] [1 4] [2 0 0 6 0 8 4 2 6 4 2 3 7 8 7 3 9 5 7 9 8 2 9 5] [3 9 8] [7 1 4 9 7 4 5 9] [3 3 3] [9 0 7 8] [3 9 4 7 2 7 8 0 3 0] [8 2 2 7 3 9 3 2] [2 9 0 8 5 4 1 8 5 5 6 2 0 9 2 7 7 9 2 7] [3 6] [1 2 7 7 4 4 2 9]] [[9 8] [8] [5 8 2] [7] [5 1] [4] [2] [0 0 6] [0] [8 4 2] [6 4] [2] [3] [7 8] [7 3] [9] [5 7 9] [8 2] [9 5] [3] [9 8] [7 1 4] [9 7] [4 5 9] [3 3] [3] [9 0] [7 8] [3] [9] [4] [7 2] [7 8] [0] [3 0] [8 2] [2] [7 3] [9 3] [2] [2] [9] [0] [8 5 4] [1 8] [5 5] [6] [2 0] [9] [2] [7 7 9] [2 7] [3 6] [1 2] [7 7] [4 4 2] [9]]
Classificação
Aqui está um snippet de pilha para gerar uma classificação regular e uma visão geral dos vencedores por idioma.
Para garantir que sua resposta seja exibida, inicie-a com um título, usando o seguinte modelo de remarcação:
# Language Name, N bytes
onde N
está o tamanho do seu envio. Se você melhorar sua pontuação, poderá manter as pontuações antigas no título, identificando-as. Por exemplo:
# Ruby, <s>104</s> <s>101</s> 96 bytes
<script>site = 'meta.codegolf'; postID = 5314; isAnswer = true; QUESTION_ID = 51719</script><script src='https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js'></script><script>jQuery(function(){var u='https://api.stackexchange.com/2.2/';if(isAnswer)u+='answers/'+postID+'?order=asc&sort=creation&site='+site+'&filter=!GeEyUcJFJeRCD';else u+='questions/'+postID+'?order=asc&sort=creation&site='+site+'&filter=!GeEyUcJFJO6t)';jQuery.get(u,function(b){function d(s){return jQuery('<textarea>').html(s).text()};function r(l){return new RegExp('<pre class="snippet-code-'+l+'\\b[^>]*><code>([\\s\\S]*?)</code></pre>')};b=b.items[0].body;var j=r('js').exec(b),c=r('css').exec(b),h=r('html').exec(b);if(c!==null)jQuery('head').append(jQuery('<style>').text(d(c[1])));if (h!==null)jQuery('body').append(d(h[1]));if(j!==null)jQuery('body').append(jQuery('<script>').text(d(j[1])))})})</script>
Desafios relacionados
fonte
[[[1 0 9] [1 3 8]] [[1] [0 9] [1 3] [8]]]
ou[["109" "138"] ["1" "09" "13" "8"]]
seria um formato de entrada aceitável?Respostas:
CJam,
13109 bytesExperimente on-line no intérprete CJam .
Obrigado a @ MartinBüttner por sugerir o engenhoso formato de entrada de @ edc65 .
Obrigado a @ jimmy23013 por melhorar o formato de entrada e obter 3 bytes adicionais.
I / O
Entrada
As sublistas são separadas por
;
e umas das outras por,
:Resultado
Como funciona
Para cadeias de comprimento diferente,
.-
deixará caracteres na matriz, que não podem ser iguais aos números inteiros 0 ou 15.fonte
;
como separador ...ll.m27m0-!
.,
e;
são ambos sintaxe de matriz comum (e nenhum deles é usado pelo CJam). Obrigado!Pitão, 19 bytes
Experimente on-line: demonstração ou equipamento de teste
Estou usando o formato de tupla / lista de Pyth como entrada. Simplesmente substitua os espaços dos casos de teste por vírgulas.
Explicação:
Como o pseudo-código ainda é um pouco confuso, demonstrarei o algoritmo usando uma entrada de exemplo.
A
.u+NYdY
peça calcula todas as sublistas contínuas que contêm o primeiro elemento.B
é um refinamento doA
iff de cada sub-lista contínuaA
também é uma sub-lista contínua deB
(há apenas uma exceção).Portanto, simplesmente verifico se o conjunto de sublistas contínuas de
A
é um subconjunto do conjunto de sublistas contínuas deB
(gF_m.u+NYdYQ
).A única exceção é se a primeira lista de entrada contiver menos elementos que a segunda lista de entrada. Por exemplo
<Fm.u+YdYQ
, retornariaTrue
para a entrada[[1]],[[1],[2]]
.Portanto, também verifico se as listas unidas também são iguais
&...qFsMQ
.fonte
JavaScript ( ES6 ), 67
70Editar 3 bytes salvos thx @apsillers
Execute o trecho abaixo no Firefox para testar
fonte
OK
eKO
.C, 69
75Uma função com 2 parâmetros de string, retornando 0 ou 1.
Formato do parâmetro: sub-lista separada por espaços (''), elementos da lista separados por vírgulas.
Exemplo:
"1,0,9 1,3,8"
"1,0 9,1,3,8"
Menos golfe
Ideona de teste (desatualizada)
fonte
Haskell, 76 bytes
Devoluções
True
ouFalse
. Exemplo de uso:[[1,0,9],[1,3,8]] # [[1,0],[9]]
->False
.Abordagem recursiva simples: se os primeiros elementos corresponderem, continue com as caudas, ou então comece de novo, mas concatene os dois elementos na frente da segunda lista. Os casos base são: ambas as listas vazias ->
True
; ambas as listas com um único elemento -> compare-as; apenas uma lista vazia ->False
.fonte
CJam, 19 bytes
Experimente online.
I / O
Entrada
Resultado
Idéia
Cada partição pode ser identificada exclusivamente observando as duas propriedades a seguir:
A lista formada concatenando todas as sublistas.
Os "pontos de corte", incluindo os extremos da lista.
Podemos combinar os dois critérios em um, substituindo cada ponto de corte pela sub-lista de elementos do ponto de corte até o final da lista.
Para verificar se uma determinada partição é mais fina que a outra, precisamos apenas verificar se a partição mais grossa, representada como acima, é um subconjunto da mais fina e se as maiores listas de ambas as partições correspondem.
Código
Para o formulário de entrada do exemplo de E / S, a pilha mantém
antes de executar
-!
.Observe que o primeiro elemento de cada matriz possui um espaço à direita. Isso garante que comparemos a lista completa da primeira entrada com a lista completa da segunda.
fonte
CJam, 24 bytes
Algoritmo
Aqui, simplesmente usamos um algoritmo ganancioso para ver se as primeiras
N
sub-listas da segunda lista podem ser mescladas para formar a primeira sub-lista da primeira lista. Uma vezN
encontrado, removemos as primeirasN
sub-listas da segunda lista e a primeira sub-lista da primeira lista e repetimos o processo.Idealmente, se a segunda lista era um refinamento da primeira, deveríamos ficar com 2 listas vazias na pilha. Apenas verificamos e imprimimos
1
se for esse o caso. Em qualquer outra combinação, depois de iterar completamente as sub-listas da segunda lista, não terminaremos com duas listas vazias. Assim, a0
será impresso para esses casos.Expansão de código
Experimente on-line aqui ou execute o conjunto de testes completo aqui
fonte
C,
120114 bytesNão joguei muito recentemente, então pensei em experimentar isso.
Definimos uma função
R(char* s, char* t)
que retorna1
set
é uma partição refinada des
, e0
caso contrário.s
et
deve estar no formato[DDDD...][DDDD...]...
Onde cada umD
é outro elemento de um dígito.Código de teste:
O texto acima imprime o seguinte:
Parece funcionar, pelo menos.
fonte
Haskell,
525053 bytesCompletamente diferente do meu outra solução . Usa o mesmo formato de entrada inteligente que a resposta do @ edc65 , ou seja, os elementos são separados por
,
e listados com.
Exemplo de uso:
"1,0,9,1,3,8" # "1,0,9 1,3,8"
->True
.O segundo parâmetro é um refinamento do primeiro, se eles tiverem elementos iguais em todas as posições ou se o primeiro for
,
. Eu tenho que acrescentar um token final exclusivo (->..
) aos dois parâmetros, porquezipWith
trunca o parâmetro mais longo e, por exemplo"1,2,3" # "1,2"
, também seriaTrue
.fonte
(\a b->a==b||a>b)
é justo(>=)
."."
vez de".."
trabalhar também?"2"#"1"
porque as funções apenas verifica se os valores são maiores, não é igual"."
não funcionará, porque daria um falso positivo para o"2,1" # "2"
qual seria expandido primeiro"2,1." # "2."
e depois truncado porzipWith
para"2," # "2."
. Uma vírgula na primeira string corresponde a tudo.Mathematica, 65 bytes
fonte
Matemática com expressões regulares é divertida!
ES6 Javascript, 53 caracteres
Javascript vintage, 70 caracteres
Usa o mesmo formato de entrada que a resposta do edc65 .
Demonstração completa, incluindo todos os casos de teste aqui.
fonte
Mathematica, 55 bytes
Isso define uma função sem nome, levando as duas partições em uma única lista , em ordem inversa (isto é
Y
, primeiro,X
segundo).Explicação
Isso verifica se as duas partições são realmente da mesma lista.
Esta é uma forma golfe da minha abordagem nesta questão sobre o Mathematica.SE , que inspirou esse desafio. Basicamente, uma partição é definida como um número de índices onde as divisões são inseridas, e isso verifica se todas as posições de divisão
X
também aparecemY
, acumulando os comprimentos das sublistas.fonte
Python 2,
6851 bytesObrigado ao xnor por uma economia considerável de bytes!
Função anônima que pega duas cadeias de caracteres do formulário
"1,0,9 1,3,8"
(extraídas da resposta C de edc65 ) e retornaTrue
orFalse
. A nova versãomap(None)
não funciona mais no Python 3.Suíte de teste:
Solução anterior de 92 bytes que recebe entradas como
"109 138"
:fonte
None
mas o outro índice possui um número, poisi==j or"0">i>j
não pode ser mantido.i==','
. Isso permite que você combine os testes comoi in[',',j]
(não podemos fazeri in ','+j
), porquej
pode serNone
.b
houver um número naquele local?" ... esquecendo que, com este formato de entrada, isso não é possível.