Objetivo: Escreva um programa ou função que imprima uma sequência de entrada em uma forma sinusoidal.
O senoide ASCII
Aqui está um período do sinusóide:
.......
... ...
.. ..
. .
. .
. .
. . .
. .
. .
. .
.. ..
... ...
.......
Observe que há exatamente um ponto em cada coluna.
- Cada caractere na sequência de entrada substituirá um ponto na forma acima, da esquerda para a direita.
- Os espaços na entrada devem ser gerados como caracteres normais, no lugar de um ponto.
- O caractere inicial corresponde ao ponto mais à esquerda na figura acima.
- Este é apenas um período, as entradas podem ser maiores que o número de pontos acima.
Entrada
- As entradas são cadeias ASCII que contêm apenas caracteres entre o decimal ASCII 32 (espaço) e o decimal ASCII 126 (Tilde ~).
- As entradas sempre serão apenas uma linha (sem quebras de linha).
- As entradas podem ser obtidas via STDIN, parâmetros de função, argumentos de linha de comando ou qualquer coisa semelhante.
Saída
- A saída deve ser impressa exatamente como nos casos de teste fornecidos.
- Os espaços à direita nas linhas são permitidos desde que o comprimento da linha com esses espaços à direita não exceda o comprimento da linha mais longa (aquela com o último caractere).
- Nenhuma linha inicial / final é permitida.
Casos de teste
- Entrada:
.................................................
Saída:
.......
... ...
.. ..
. .
. .
. .
. . .
. .
. .
. .
.. ..
... ...
.......
- Entrada:
Programming Puzzles & Code Golf Stack Exchange is a question and answer site for programming puzzle enthusiasts and code golfers. It's 100% free, no registration required.
Saída:
ng Puzz ion and siasts stratio
mmi les est an thu and egi n r
ra & qu sw en c r eq
g e o o u
o C a r e d n i
r o l e r
P d s s z , e
e i i z g e d
t u o e .
G e e p l r
ol ng f g fe f
f S cha or min rs. 00%
tack Ex program It's 1
- Entrada:
Short text.
Saída:
t.
tex
t
r
o
h
S
- Entrada:
The quick brown fox jumps over the lazy dog
Saída:
brown
ick fox
qu j
u
e m
h p
T s
o
v
er
th dog
e lazy
Pontuação
Isso é código-golfe , então o programa ou função mais curto em bytes vence.
sin
função para reproduzi-lo, mas as posições são um pouco fora.)Respostas:
Pitão, 59 bytes (57 caracteres)
Demonstração.
Uma tabela de pesquisa binária é codificada dentro
, com o valor 3912. Isso é convertido em binário, dando[1, 1, 1, 1, 0, 1, 0, 0, 1, 0, 0, 0]
. Isso é tratado como as diferenças entre alturas consecutivas. Anexando um 6, formando todos os prefixos e mapeando cada um para sua soma, o primeiro quarto da onda é gerado.sM._+6jC\2
avalia[6, 7, 8, 9, 10, 10, 11, 11, 11, 12, 12, 12, 12]
como descrito acima. Em seguida, o código concatena no verso dessa string para formar a primeira metade da onda e, em seguida, subtrai-o de 12 para fornecer a onda inteira.Em seguida, formamos linhas de cada caractere de entrada seguidas por 12 espaços. Essa linha é girada para a direita pelo parâmetro de altura da onda correspondente a esse local e, em seguida, as linhas são transpostas e unidas em novas linhas.
Em seguida, retiramos as linhas em branco à esquerda e à esquerda. No entanto, não podemos remover linhas em branco à esquerda ou à direita que tenham espaços da entrada. Isso é implementado substituindo espaços na entrada por tabs (
C9
), que não podem estar na entrada, eliminando linhas em branco e transformando as guias novamente em espaços.fonte
Python 2, 156 bytes
Explicação
O código inteiro simplesmente cria um bloco de espaços (
o
) e substitui os espaços corretos pelas letras da entradat
.A variável
l
armazena uma lista de compensações da parte superior. Para que on
th caractere det
esteja na linhal[n]
.O bytearray
o
serve como uma sequência mutável, pois as sequências são imutáveis em python.-~h
é o mesmo queh+1
economiza espaço porque não preciso de parênteses.fonte
Java,
219209199 bytesEu ainda sou um novato aqui e espero que seja compatível com as regras a introdução de uma subfunção (quando os bytes dessa função forem contados, é claro). Caso contrário, tentarei converter a
sin
função em alguma pesquisa inteligente de array ...fonte
char[]
. Aqui, seria livrar-se do()
onlength
e eliminarcharAt()
também. Se eu estiver lendo certo, você também pode usar emprint()
vez deprintln()
economizar mais alguns....a<24?s(24-a):-s(a-24);
e chame-o coms(c%48)
.Perl, 222 bytes
Requer
-E
parasay
, armazena as posições como números inteiros convertidos em números binários e a inversão da matriz provavelmente não é muito eficiente em bytes. Também tenho certeza de que há muitas economias a serem feitas, então continuarei cutucando e cutucando.Exemplo de saída:
fonte
JavaScript,
251243224220217Implementação realmente simples: ele usa uma sequência de caracteres para representar a posição y de cada caractere na onda (compensado por
a
, que é o código ASCII 97). Ele itera através de todas as linhas possíveis; se o valor y da linha atual for o mesmo que a posição y na onda, ele gravará um caractere da sequência. Há também uma limpeza no final para remover a linha, se estiver completamente em branco.Observe que a saída aparecerá instável na
alert()
janela, se não estiver usando uma fonte monoespaçada, você pode alterá-laconsole.log()
para verificar se a saída está correta.EDIT1:
++
e--
existe.EDIT2: A remoção da linha em branco agora é feita no mesmo loop que o restante, salvando 17 caracteres. Também não precisava desses suportes, para 2 caracteres extras.
EDIT3: Não há necessidade de declarar a forma de onda como uma variável, salvando 4 caracteres.
EDIT4: Como apontado por Dom Hastings nos comentários, a contagem de bytes incluiu o retorno de carro, bem como o caractere de nova linha, atualizou a contagem de bytes para todas as revisões para excluir o retorno de carro.
EDIT5: Salvo 3 bytes, cortesia de Dom Hastings. Não implementei a
o.splice
correção, pois isso falha ao remover as linhas em branco (pelo menos no final).fonte
if(o[i++].trim().length<1)o.splice(--i,1)
poro.splice(i-(t=!o[i++].match(/\s/)),t)
, por -4,s=prompt() o=[]
pors=prompt(o=[])
:, -1 efor(y=0,i=0;y<13;++y){o[i]=""
porfor(y=i=0;y<13;++y){o[i]=""
, -2. Provavelmente, é possível combinar também os loops for para economizar mais ... Uma última coisa, vale a pena notar também que eu só tenho 220 para sua contagem de bytes atual, então seus 225 podem ser janelas em\r\n
vez de apenas o\n
que suponho que você possa ignorar (por favor me corrijam se eu estiver errado) ...for(s=prompt(),y=0;y<13;y++,v.trim()&&console.log(v))for(v="",x=0;x<s.length;x++)v+=y=="gfedccbbbaaaaaaabbbccdefghijkklllmmmmmmmlllkkjih".charCodeAt(x%48)-97?s[x]:" "
for(s=prompt(y=0);y<13;y++,v.trim()&&console.log(v))for(v="",x=0;x<s.length;x++)v+="gfedccbbbaaaaaaabbbccdefghijkklllmmmmmmmlllkkjih".charCodeAt(x%48)-97-y?" ":s[x]
Matlab,
133, 130 bytesO forro único:
E a versão expandida:
O liner único recebe entrada do console (
stdin
) e tem 130 bytes. A versão expandida substitui a entrada do console por uma definição de função (+1 byte), mas é muito mais confortável de usar no caso de teste em um loop:Descrição:
O índice de linha de cada caractere é calculado por meio período, depois espelhado e concatenado para ter um período completo.
Criamos um plano de fundo em branco de caractere de espaço em branco (mesmo comprimento da string de entrada. Colocamos cada caractere de acordo com sua posição na linha relevante. Se a string de entrada for maior que um período, o
mod
operador (modulo) quebra isso para que não Não saia do limite ao solicitar o número da linha.Caso de teste:
Salve a versão da função
textsine.m
em seu caminho e execute:irá produzir:
se você quiser testar a versão de uma linha com entrada de
stdin
, sua entrada deve ser inserida como uma únicastring
, portanto, você deve incluir sua entrada entre'
caracteres. Exemplo:Obrigado
Luis Mendo
por raspar 3 bytes ;-)fonte
s=input('');
ainda funcionasse.Scala 377 caracteres
primeiro corte. provavelmente pode obter uma fórmula melhor para traduzir
x
paray
fonte
Lisp comum, 205 bytes
Testes
Consulte http://pastebin.com/raw.php?i=zZ520FTU
Observações
Imprima a linha de saída por linha, calculando os índices nas sequências que devem ser impressas usando a função inversa senoidal
asin
. A saída não corresponde exatamente às entradas esperadas na pergunta, mas como o OP reconhece que as saídas de exemplo não são senoidais reais, acho que está tudo bem. Pelo menos, sempre há apenas um caractere escrito para cada coluna.fonte
Python 2, 172 bytes
Isso não é tão bom quanto a resposta de Alex L , mas é bem próximo. Recebe entrada da entrada padrão e funciona melhor em um
.py
arquivo.Decidi construir a saída transposta (cada coluna é uma linha) e depois transpor o resultado, já que em python a transposição de uma matriz é
map(*m)
.l
: A representação binária de9960000
(após cortar o"0b"
debin
) é100101111111101001000000
. Este é o "passo" da onda senoidal em cada coluna, começando no último caractere do ponto mais baixo. Copio esta lista, nego cada número e colo-a no final de si mesma para formar o que é efetivamente um derivado da função.s
: Essa é a variável que controla em qual linha (coluna na transposição) o próximo caractere é inserido.o
: Saída final, transpostai
: Mantém o controle do período das ondas senoidais. Começa às 9, poisl
é ligeiramente deslocada.No
for
loop, crio uma lista de 13 espaços (eu estava usando bytes, mas as listas de caracteres têm uma instrução de impressão mais curta) e, em seguida, substituo os
caractere pelo caractere de entrada. Anexeb
ao final deo
, adicione a etapa apropriada aes
incrementei
.Eu esperava que a
print
declaração fosse tão simples quanto\n'.join(*zip(o))
, mas não tive tanta sorte.zip(*o+['\n'*13])[::-1]
anexa uma coluna de novas linhas e depois inverte e transpõe a coisa toda (sem a inversão, a onda senoidal está de cabeça para baixo),sum(...,())
concatena as tuplas juntas em uma tupla de caracteres e, em seguida,''.join(...)
concatena os caracteres e a imprime.Outras coisas que tentei foram criar uma matriz de espaços de 12 caracteres e inserir o novo caractere no local apropriado, e substituir
l+=[-c for c in l];
por algum tipo de matemática por algum tipo de multiplicação1
e-1
com o resultado da indexaçãol
, mas nada que eu pudesse descobrir acabou sendo mais curto.fonte
Mathematica, 131 bytes
São 131 caracteres, incluindo os três para
i=foo;
. Essa parecia uma maneira razoável de receber a opinião; Eu poderia ter colocado direto na definiçãoc
e salvo alguns golpes, mas isso parece injusto.É bem direto - quase até legível. Ele divide a cadeia de caracteres em uma lista de caracteres e, em seguida, coloca esses caracteres em uma matriz esparsa nas posições determinadas a partir de
Table
(qualquer ponto da matriz sem um caractere padrão para um espaço). As linhas são montadas separadamente e as novas linhas são espalhadas entre elas. O StringJoin final une tudo.NB: Como algumas outras soluções, isso pode não ser realmente válido porque produz um sinusóide real, e não o exemplo (bonito) artesanal.
Testes:
fonte