Pergunta

Responda com o mais curto código -fonte possível para um programa que converte um texto simples arbitrário em seu texto cifrado correspondente, seguindo a entrada e a saída da amostra que eu forneci abaixo. Pontos de bônus* pelo menor tempo da CPU ou pela menor quantidade de memória usada.

Exemplo 1:

Texto simples: A rápida raposa marrom pula sobre o cachorro preguiçoso. Supercalifragilisticexpialidocious!

CipherText: eth kiquc nobrw xfo smjup rvoe ethalz .odg! uioiapeislgriarpsueclfaiitcxildcos

Exemplo 2:

Texto simples: 123 1234 12345 123456 1234567 12345678 123456789

CipherText: 312 4213 53124 642135 7531246 86421357 975312468

Regras:

  1. A pontuação é definida para ser incluída na palavra em que é mais próxima.
  2. O centro de uma palavra é definido como teto ((strlen (word) +1)/2).
  3. O espaço em branco é ignorado (ou entrou em colapso).
  4. Palavras estranhas se movem para a direita primeiro. Até as palavras se movem para a esquerda primeiro.

Você pode pensar nisso como ler todos os outros personagens para trás (a partir do final da palavra), seguidos pelos personagens restantes para a frente. Corporação => xoxpxrxtxox => niaorcoprto.

Obrigado àqueles que apontaram a inconsistência na minha descrição. Isso levou muitos de vocês pelo caminho errado, pelo qual peço desculpas. A regra nº 4 deve esclarecer as coisas.

*Os pontos de bônus só serão concedidos se Jeff Atwood decidir fazê -lo. Como não chequei com ele, as chances são pequenas. Desculpe.

Foi útil?

Solução

Python, 50 caracteres

Para entrada in i:

' '.join(x[::-2]+x[len(x)%2::2]for x in i.split())

Versão alternativa que lida com seu próprio IO:

print ' '.join(x[::-2]+x[len(x)%2::2]for x in raw_input().split())

Um total de 66 caracteres, se incluindo o espaço em branco. (Tecnicamente, o print pode ser omitido se executar de uma linha de comando, pois o valor avaliado do código é exibido como saída por padrão.)


Versão alternativa usando reduce:

' '.join(reduce(lambda x,y:y+x[::-1],x) for x in i.split())

59 caracteres.

Versão original (pares e ímpares, vá direto primeiro) para uma entrada em i:

' '.join(x[::2][::-1]+x[1::2]for x in i.split())

48 caracteres, incluindo espaço em branco.

Outra versão alternativa que (embora um pouco mais) é um pouco mais eficiente:

' '.join(x[len(x)%2-2::-2]+x[1::2]for x in i.split())

(53 caracteres)

Outras dicas

J, 58 caracteres

>,&.>/({~(,~(>:@+:@i.@-@<.,+:@i.@>.)@-:)@<:@#)&.><;.2,&' '

Haskell, 64 caracteres

unwords.map(map snd.sort.zip(zipWith(*)[0..]$cycle[-1,1])).words

Bem, ok, 76 se você adicionar o requisito "import List".

Python - 69 chars

(incluindo espaço em branco e linebreaks)

Isso lida com toda a E/S.

for w in raw_input().split():
 o=""
 for c in w:o=c+o[::-1]
 print o,

Perl, 78 caracteres

Para entrada in $_. Se isso não for aceitável, adicione seis caracteres para qualquer um $_=<>; ou $_=$s; no inicio. A nova linha é apenas para legibilidade.

for(split){$i=length;print substr$_,$i--,1,''while$i-->0;
print"$_ ";}print $/

C, 140 caracteres

Bem formatado:

main(c, v)
  char **v;
{
  for( ; *++v; )
  {
    char *e = *v + strlen(*v), *x;
    for(x = e-1; x >= *v; x -= 2)
      putchar(*x);
    for(x = *v + (x < *v-1); x < e; x += 2)
      putchar(*x);
    putchar(' ');
  }
}

Comprimido:

main(c,v)char**v;{for(;*++v;){char*e=*v+strlen(*v),*x;for(x=e-1;x>=*v;x-=2)putchar(*x);for(x=*v+(x<*v-1);x<e;x+=2)putchar(*x);putchar(32);}}

Lua

130 Função de char, programa de funcionamento 147 Char

Lua não recebe amor suficiente no Code Golf - talvez porque seja difícil escrever um programa curto quando você tem palavras -chave longas como function/end, if/then/end, etc.

Primeiro, escrevo a função de maneira detalhada com explicações, depois a reescrevo como uma função comprimida e independente, então eu chamo essa função no solteiro argumento especificado na linha de comando.

Eu tive que formatar o código com <pre></pre> Tags porque Markdown faz um trabalho horrível de formatar Lua.

Tecnicamente, você pode obter um programa de execução menor, envolvendo a função, mas é mais modular assim :)

t = "The quick brown fox jumps over the lazy dog. Supercalifragilisticexpialidocious!"
T = t:gsub("%S+", -- for each word in t...
                  function(w) -- argument: current word in t
                    W = "" -- initialize new Word
                    for i = 1,#w do -- iterate over each character in word
                        c = w:sub(i,i) -- extract current character
                        -- determine whether letter goes on right or left end
                        W = (#w % 2 ~= i % 2) and W .. c or c .. W
                    end
                    return W -- swap word in t with inverted Word
                  end)


-- code-golf unit test
assert(T == "eTh kiquc nobrw xfo smjup rvoe eth yalz .odg !uioiapeislgriarpSueclfaiitcxildcos")

-- need to assign to a variable and return it,
-- because gsub returns a pair and we only want the first element
f=function(s)c=s:gsub("%S+",function(w)W=""for i=1,#w do c=w:sub(i,i)W=(#w%2~=i%2)and W ..c or c ..W end return W end)return c end
--       1         2         3         4         5         6         7         8         9        10        11        12        13
--34567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678901234567890
-- 130 chars, compressed and written as a proper function

print(f(arg[1]))
--34567890123456
-- 16 (+1 whitespace needed) chars to make it a functioning Lua program, 
-- operating on command line argument

Resultado:

$ lua insideout.lua 'The quick brown fox jumps over the lazy dog. Supercalifragilisticexpialidocious!'
eTh kiquc nobrw xfo smjup rvoe eth yalz .odg !uioiapeislgriarpSueclfaiitcxildcos

Ainda sou muito novo na Lua, então gostaria de ver uma solução mais curta, se houver uma.


Para uma cifra mínima em todos os args para stdin, podemos fazer 111 chars:

for _,w in ipairs(arg)do W=""for i=1,#w do c=w:sub(i,i)W=(#w%2~=i%2)and W ..c or c ..W end io.write(W ..' ')end

Mas essa abordagem produz um espaço à direita, como algumas das outras soluções.

Para uma entrada em s:

f=lambda t,r="":t and f(t[1:],len(t)&1and t[0]+r or r+t[0])or r
" ".join(map(f,s.split()))

Python, 90 caracteres, incluindo espaço em branco.

Tcl

125 caracteres

set s set f foreach l {}
$f w [gets stdin] {$s r {}
$f c [split $w {}] {$s r $c[string reverse $r]}
$s l "$l $r"}
puts $l

Bash - 133, assumindo que a entrada está na variável $ w

Bonito

for x in $w; do 
    z="";
    for l in `echo $x|sed 's/\(.\)/ \1/g'`; do
        if ((${#z}%2)); then
            z=$z$l;
        else
            z=$l$z;
        fi;
    done;
    echo -n "$z ";
done;
echo

Comprimido

for x in $w;do z="";for l in `echo $x|sed 's/\(.\)/ \1/g'`;do if ((${#z}%2));then z=$z$l;else z=$l$z;fi;done;echo -n "$z ";done;echo

Ok, então ele produz um espaço à direita.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top