Comparação quase lexicográfica de listas


9

Entrada

Duas listas Ae Bnúmeros inteiros não negativos.

Resultado

Qualquer um 1, 0ou -1, dependendo se Aé maior que, igual a, ou menor do que Bno que diz respeito à ordem léxicografica torcido , tal como definido abaixo. Se você quiser, você pode substituir 1, 0e -1com quaisquer outros três valores constantes.

A ordem lexicográfica distorcida é como a ordem lexicográfica comum, na qual você compara as listas elemento por elemento e decide a ordem delas no primeiro índice diferente. No entanto, na versão distorcida, usamos uma ordem diferente para números inteiros não negativos em cada índice. Ou seja, em todo índice i(a indexação começa em 1), a ordem dos primeiros inúmeros inteiros não negativos (de 0para i-1) é revertida e eles são movidos acima de todos os outros números. Além disso, o "elemento ausente" que significa que uma lista é mais curta que a outra é movida diretamente abaixo i-1. Visualmente, a ordem no índice ié

i < i+1 < i+2 < i+3 < ... < [missing element] < i-1 < i-2 < i-3 < ... < 2 < 1 < 0

Observe que o primeiro ...denota infinitamente muitos números. Isso significa que as seguintes listas estão em ordem crescente em relação à ordem lexicográfica distorcida:

[3,2,3,4]
[3,2,3,5]
[3,2,3,10]
[3,2,3,1341]
[3,2,3]
[3,2,3,3]
[3,2,3,2]
[3,2,3,1]
[3,2,3,0]

Regras

Você pode dar um programa completo ou uma função. A menor contagem de bytes vence e as brechas padrão não são permitidas.

Casos de teste

Output 1:
[0] []
[] [1]
[] [1,2,1,2]
[2,1] [1,1]
[0,1,2] [0,2,1]
[3,0] [3,1]
[3,1] [3]
[2] [2,2]
[2] [2,23]
[2,24] [2,23]
[2,1] [2,23]

Output 0:
[] []
[0] [0]
[1,1] [1,1]
[2,1,2] [2,1,2]

Output -1:
[1,2,1,1,2] [1,2,1,1,1]
[1,2,1,1,5] [1,2,1,1,4]
[1,2,1,1,5] [1,2,1,1]
[1,2,1] [1,2,1,1]
[1,2,1,1,5] [1,2,1,1,6]
[1,2,1,1,6] [1,2,1,1,7]

As listas de entrada são indexadas de 0, de 1 ou do que for apropriado para o nosso idioma?
Peter Taylor

@ PeterTaylor De 1. Vou esclarecer isso.
Zgarb

Posso usar a própria enumeração de Haskell para obter resultados de comparação em vez de -1/0/1 para a saída?
John Dvorak

@JanDvorak Eu vou permitir isso e editar o desafio.
Zgarb

Respostas:


1

CJam - 57

q:S~=0{S~]:A:,~e>{A{_,I>{I=_I>0{W*2}?}1?[\]}%}fI]z~>2*(}?

Sim, ainda é muito longo ...

Experimente online

Breve explicação:
O código gera 0 se as matrizes forem iguais no sentido tradicional; caso contrário, converte cada item de cada matriz em uma matriz de 2 elementos: [0 a i ] se a i > i (com base em 0), [1 o que seja] se a i estiver ausente e [2 -a i ] se a i <= i. No processo, a matriz mais curta também é estendida para o tamanho maior. Em seguida, as matrizes transformadas são comparadas lexicograficamente e o resultado é ajustado para -1/1.


3

Python 2, 76 bytes

c=lambda*a:cmp(*[[(max(i-x,-1),x)for i,x in enumerate(L)]+[(0,)]for L in a])

Isso substitui cada número inteiro nas duas listas por uma tupla de 2 para contabilizar a ordem distorcida. O Python 2 cmpembutido faz o resto.

Uso:

>>> c([1,2,1,1,6], [1,2,1,1,7])
-1

11
Como isso explica uma lista mais curta entre diferentes listas mais longas ( [3,2,3,1341] < [3,2,3] < [3,2,3,0]?
nutki 26/02/15

@nutki adiciona a tupla (0,)ao final de cada lista, que é maior que qualquer (-1, x)e menor que (i-x, x)quando i-x >= 0.
grc

Ah, claro. Eu não sou alfabetizado em Python.
nutki

1

Perl, 74

Sem boas funções de manipulação de array, o perl não é a ferramenta ideal para o trabalho, mas funciona.

#!perl -pa
$i=0,s/\d+,?/$s=sprintf"%9d",$&;$&>$i++?$s:~$s/ge for@F;$_=$F[0]cmp$F[1]

Teste- me .


1

J, 95 bytes

(Não é super curto, mas tanto faz. Definitivamente jogável.)

f=.4 :0
m=.>:>./x,y
t=.(|+(1+m)*0>:*)@(i.@#-~])@(],m$~>&#*-&#)
x(t~(*@-&((m+#x,y)&#.))t)y
)

Passando em todos os casos de teste. (Ótimo conjunto de casos de teste! Obrigado!)

Método:

  • Preenchendo a lista mais curta com maxvalue + 1 ( m=.>:>./x,y).(],m$~>&#*-&#
  • Transformando elementos da lista para que a comparação normal possa ser usada. (|+(1+m)*0>:*)@(i.@#-~])
  • Calculando dois números baseX da lista dois com X suficiente. ((m+#x,y)&#.)
  • Retornando o sinal da diferença de dois números.*@-&

0

Mathematica, 65

f=-Order@@MapIndexed[If[#>Last@#2,#,a-b#]&,PadRight[{##}+1],{2}]&

Uso:

f[{1, 2, 1, 1, 6}, {1, 2, 1, 1, 7}]

-1

Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.