fundo
A maioria dos editores de texto (meio decentes) permite navegar pelo texto usando as teclas de seta. Para cima e para baixo, você pode navegar pelas linhas, enquanto a esquerda e a direita se movem através de uma linha, mas também se movimentam. Além disso, se a linha for menor que a posição X do seu cursor, o cursor aparecerá no final da linha, mas retornará à mesma posição X se você continuar se movendo para cima ou para baixo. Talvez a seguinte explicação visual ajude:
Exemplos de movimento
Uma simples amostra de texto pode ser assim. O cursor será inserido entre dois caracteres neste texto ou no final.
-----
---
------
let's put the cursor here:
X-----
---
------
move down (v):
-----
X---
------
move left (<):
-----X
---
------
v
-----
---X
------
v (notice how the X position of the cursor has been maintained)
-----
---
-----X-
^
-----
---X
------
> (more line wrapping)
-----
---
X------
<
-----
---X
------
^ (the X-position from earlier is no longer maintained due to the left-right motion)
---X--
---
------
O desafio
Dadas várias linhas de teste ASCII, encontre o caminho mais curto desde o local inicial até o local final. O local inicial é representado por ^
e o local final é representado por $
, e haverá apenas um de cada. Eles não são considerados parte do texto e não contribuem para o "comprimento" dessa linha.
A entrada consistirá em várias linhas de texto não em branco. A saída será uma série de ^v<>
caracteres que mostram um dos caminhos mais curtos. Opcionalmente, você pode assumir uma nova linha adicional no final de cada uma, mas que não está incluída como parte do texto navegável.
Você pode escrever um programa ou função nomeada. O vencedor será o envio mais curto, medido em bytes.
Exemplo de E / S
^Squares
are
fun$ny
vv<v (which is better than the naive vv>>>)
Squares
^are
funny$
<vv
Alp$habet^
Song
v<^
Mary had a little lamb,
His fleece was white as snow,
And$ everywhere that ^Mary went,
The lamb was sure to go.
^^>>>>v>>>
$^degenerate case
(no output)
v<vv
, certo? Ou isso terminaria após o último caractere nessa linha?Respostas:
CJam, 139 bytes
Bem, isso levou muitas horas para chegar a algo que parece feito. Parece que o tempo necessário para otimizar agressivamente o código CJam é algo maior que O (n) em relação ao tamanho do código ...
Você pode experimentá-lo on-line , mas, para qualquer entrada cujo melhor caminho seja pelo menos seis operações, provavelmente você deve experimentá-lo off-line com um intérprete mais rápido.
Squished:
Expandido e comentado:
No geral, esta é uma solução bastante direta. Ele "executa" os dígitos da representação da base 5 de um número de caminho que é incrementado a cada iteração, começando com 0, até que um caminho funcione. Os dígitos
1
- são4
mapeados para as operações para cima, baixo, esquerda e direita e0
não fazem nada. A primeira iteração usando um caminho de apenas0
captura o caso degenerado. Todos os outros caminhos que contêm a0
nunca são selecionados porque são apenas versões de caminhos já testados com não operações adicionais.O estado é modelado da maneira mais minimalista possível: o texto com os marcadores de início e fim removidos, a posição do cursor no texto e a "memória da coluna". As novas linhas são tratadas principalmente como qualquer outro caractere, portanto não há conceito de linha e a posição do cursor é apenas um índice. Isso simplifica a movimentação da esquerda e da direita, que são implementadas apenas como decremento e incremento (com fixação do tamanho do texto). Mover para cima e para baixo é um pouco mais complicado, mas ainda gerenciável.
A reutilização de código foi uma tática de otimização bastante vital. Exemplos disso incluem:
5
operação fictícia ao início da cadeia de caminho, que também usa a0
lógica no-op devido à indexação circular da matriz e apenas cinco operações definidas.No geral, estou muito feliz com o resultado. Esse é definitivamente o maior trabalho que eu coloquei em uma resposta de código de golfe até o momento (para algo que se encaixa em um tweet !?). O tempo de execução é bastante abismal, no entanto. CJam não é exatamente o idioma mais rápido para começar e esse algoritmo tem uma complexidade de algo como O (m * 5 n ) , onde m é o tamanho da entrada en é o tamanho da saída. Ainda bem que a velocidade não conta!
fonte
Python 2: 446
Solução simples. Estou realizando uma pesquisa pela primeira vez.
t
itera sobre todos os caminhos diferentes. Eu convertot
em base5
, mas apenas uso as entradas que são diferentes de zero.1
está alto,2
baixo,3
esquerda e4
direita.Eu mantenho a posição atual do cursor em 3 variáveis
x
,y
ez
.x
é a linha,y
a posição da coluna ez
a posição da coluna 'oculta', se você subir ou descer e a linha for muito curta. Muitos ifs decidem como a variável muda durante um movimento.O pré-processamento é realmente demorado, as 4 primeiras linhas executam apenas esta tarefa.
O longo caso de teste leva muito tempo. O algoritmo tem uma complexidade de O (N * 5 ^ N), onde N é o comprimento da solução mais curta.
Uso: insira as linhas como uma única sequência (linhas separadas por
\n
) como"Alp$habet^\nSong"
fonte
CJam - 274
Ainda não há resposta? Ok, aqui está um :)
Experimente em http://cjam.aditsu.net/ ..., exceto pelo exemplo de Mary ou algo desse tamanho, você provavelmente desejará o interpretador java .
fonte