Programa de gato simple


84

Una de las tareas estándar más comunes (especialmente cuando se muestran lenguajes de programación esotéricos) es implementar un "programa cat" : lea todo STDIN e imprímalo en STDOUT. Si bien esto lleva el nombre de la utilidad de shell Unix cat, por supuesto, es mucho menos potente que el real, que normalmente se utiliza para imprimir (y concatenar) varios archivos leídos del disco.

Tarea

Debe escribir un programa completo que lea los contenidos de la secuencia de entrada estándar y los escriba textualmente en la secuencia de salida estándar. Si y solo si su idioma no admite flujos de entrada y / o salida estándar (como se entiende en la mayoría de los idiomas), puede tomar estos términos como su equivalente más cercano en su idioma (por ejemplo, JavaScript prompty alert). Estas son las únicas formas admisibles de E / S, ya que cualquier otra interfaz cambiaría en gran medida la naturaleza de la tarea y haría que las respuestas fueran mucho menos comparables.

La salida debe contener exactamente la entrada y nada más . La única excepción a esta regla es la salida constante del intérprete de su idioma que no se puede suprimir, como un saludo, códigos de color ANSI o sangría. Esto también se aplica a las nuevas líneas finales. Si la entrada no contiene una nueva línea final, ¡la salida tampoco debería incluir una! (La única excepción es si su idioma siempre imprime una nueva línea final después de la ejecución).

La salida a la secuencia de error estándar se ignora, siempre que la secuencia de salida estándar contenga la salida esperada. En particular, esto significa que su programa puede terminar con un error al llegar al final de la secuencia (EOF), siempre que no contamine la secuencia de salida estándar. Si hace esto, le animo a que también agregue una versión sin errores a su respuesta (como referencia).

Como esto pretende ser un desafío dentro de cada idioma y no entre idiomas, existen algunas reglas específicas del idioma:

  • Si es posible en su idioma distinguir bytes nulos en el flujo de entrada estándar del EOF, su programa debe admitir bytes nulos como cualquier otro bytes (es decir, también deben escribirse en el flujo de salida estándar).
  • Si es posible en su idioma admitir una secuencia de entrada infinita arbitraria (es decir, si puede comenzar a imprimir bytes en la salida antes de presionar EOF en la entrada), su programa debe funcionar correctamente en este caso. Como ejemplo yes | tr -d \\n | ./my_catdebería imprimir una corriente infinita de ys. Depende de usted con qué frecuencia imprime y vacía el flujo de salida estándar, pero debe garantizarse que suceda después de un período de tiempo finito, independientemente del flujo (esto significa, en particular, que no puede esperar un carácter específico como un salto de línea antes de imprimir).

Agregue una nota a su respuesta sobre el comportamiento exacto con respecto a bytes nulos, flujos infinitos y salidas extrañas.

Reglas adicionales

  • No se trata de encontrar el idioma con la solución más corta para esto (hay algunos en los que el programa vacío hace el truco), se trata de encontrar la solución más corta en cada idioma. Por lo tanto, ninguna respuesta se marcará como aceptada.

  • Las presentaciones en la mayoría de los idiomas se puntuarán en bytes en una codificación preexistente apropiada, generalmente (pero no necesariamente) UTF-8.

    Algunos idiomas, como las carpetas , son un poco difíciles de puntuar. En caso de duda, pregunte por Meta .

  • Siéntase libre de usar un idioma (o versión de idioma) incluso si es más nuevo que este desafío. Los idiomas escritos específicamente para enviar una respuesta de 0 bytes a este desafío son juegos justos pero no particularmente interesantes.

    Tenga en cuenta que debe haber un intérprete para que se pueda probar el envío. Está permitido (e incluso alentado) escribir este intérprete usted mismo para un lenguaje previamente no implementado.

    También tenga en cuenta que las lenguas no tienen que cumplir con los criterios habituales para lenguajes de programación .

  • Si su idioma de elección es una variante trivial de otro lenguaje (potencialmente más popular) que ya tiene una respuesta (piense en dialectos BASIC o SQL, shells Unix o derivados triviales de Brainfuck como Headsecks o Unary), considere agregar una nota a la respuesta existente que la misma solución o una muy similar también es la más corta en el otro idioma.

  • A menos que se hayan anulado anteriormente, se aplican todas las reglas estándar de , incluido http://meta.codegolf.stackexchange.com/q/1061 .

Como nota al margen, no desestime las respuestas aburridas (pero válidas) en idiomas donde no hay mucho para jugar golf; todavía son útiles para esta pregunta, ya que trata de compilar un catálogo lo más completo posible. Sin embargo, sobre todo vota las respuestas en idiomas en los que el autor realmente tuvo que esforzarse para jugar golf en el código.

Catálogo

El Fragmento de pila al final de esta publicación genera el catálogo a partir de las respuestas a) como una lista de la solución más corta por idioma yb) como una tabla de clasificación general.

Para asegurarse de que su respuesta se muestre, comience con un título, utilizando la siguiente plantilla de Markdown:

## Language Name, N bytes

¿Dónde Nestá el tamaño de su envío? Si mejora su puntaje, puede mantener los puntajes antiguos en el título, tachándolos. Por ejemplo:

## Ruby, <s>104</s> <s>101</s> 96 bytes

Si desea incluir varios números en su encabezado (por ejemplo, porque su puntaje es la suma de dos archivos o desea enumerar las penalizaciones de la bandera del intérprete por separado), asegúrese de que el puntaje real sea el último número en el encabezado:

## Perl, 43 + 2 (-p flag) = 45 bytes

También puede hacer que el nombre del idioma sea un enlace que luego aparecerá en el fragmento:

## [><>](http://esolangs.org/wiki/Fish), 121 bytes


52
Bash, 3 bytes :cat
TheDoctor

3
@TheDoctor Supongo que esto caería en la regla de "no usar un incorporado que hace exactamente lo que se necesita".
Paŭlo Ebermann

55
@ PaŭloEbermann No existe tal regla y ya no se acepta la escapatoria estándar correspondiente. (De hecho, ya hay una shrespuesta usando catque también contiene una solución más corta usando dd.)
Martin Ender

1
Si solo utilizara métodos estándar de entrada y salida: ///, 0 bytes .
Camarada SparklePony

1
@SparklePony Excepto que tendrías que escapar de las barras diagonales y las barras diagonales inversas.
Martin Ender

Respuestas:


73

sed, 0


El sedprograma vacío hace exactamente lo que se requiere aquí:

$ printf "abc\ndef" | sed ''
abc
def$ 

3
¿Qué pasa si uno escribe yes | tr -d \\n | sed ''?
BenGoldberg

@BenGoldberg De forma predeterminada, sed funciona por línea, por lo que en este caso continuará absorbiendo yeses en un búfer de patrón hasta que se quede sin memoria. Una advertencia, supongo ...
Digital Trauma

POSIX exige que el espacio del patrón debe tener un tamaño de al menos 8192 bytes, IIRC. Sé que la implementación de GNU tiene un espacio de patrón dinámico, limitado solo por la memoria disponible, por lo que está bastante seguro en eso.
Toby Speight

59

Ziim , 222 201 196 185 182 bytes

    ↓ ↓

 ↓ ↓     ↓
 ↗ ↗↙↔↘↖ ↖
 ↓↓⤡⤢  ⤢↙
↘ ↖⤡ ↖
  ↙
  ↕↘ ↑ ↙
→↘↖↑ ↙ ↑
→↖   ↑
→↖↘ ↙
  ↑↓↑

   ⤡

Esto probablemente no se mostrará correctamente en su navegador, por lo que aquí hay un diagrama del código:

ingrese la descripción de la imagen aquí

No puedo pensar en una estructura más simple para resolver el problema en Ziim, pero estoy seguro de que el código real sigue siendo bastante fácil de encontrar.

Ziim no puede manejar flujos infinitos porque solo es posible imprimir cualquier cosa al final del programa.

Explicación

Dado que Ziim tiene un modelo de flujo de control declarativo bastante único, un algoritmo de pseudocódigo imperativo no lo cortará aquí. En cambio, explicaré los conceptos básicos de Ziim y presentaré la estructura ordenada del código anterior (de manera gráfica similar) como el arte ASCII.

El flujo de control en Ziim ocurre por todas partes: cada flecha que no está apuntada por otra flecha inicializa un "hilo" que se procesa independientemente de los demás (no realmente en paralelo, pero no hay garantías en qué orden se procesan) , a menos que los sincronice mediante concatenación). Cada uno de estos hilos contiene una lista de dígitos binarios, comenzando como {0}. Ahora cada flecha en el código es una especie de comando que tiene una o dos entradas y una o dos salidas. El comando exacto depende de cuántas flechas lo apuntan desde qué orientaciones.

Aquí está la lista de los comandos, donde m -> nindica que el comando toma mentradas y produce nsalidas.

  • 1 -> 1, no-op : simplemente redirige el hilo.
  • 1 -> 1, invert : niega cada bit en el hilo (y también lo redirige).
  • 1 -> 1, leer : reemplaza el valor del hilo por el siguiente bit de STDIN, o por la lista vacía si hemos alcanzado EOF.
  • 2 -> 1, concatenate : esta es la única forma de sincronizar hilos. Cuando un hilo golpea un lado de la flecha, se suspenderá hasta que otro hilo golpee el otro lado. En ese punto, se concatenarán en un solo hilo y continuarán la ejecución.
  • 2 -> 1, etiqueta : esta es la única forma de unir diferentes rutas de ejecución. Esto es simplemente un no-op que tiene dos entradas posibles. Por lo tanto, los hilos que ingresan a la "etiqueta" a través de cualquiera de las rutas simplemente serán redirigidos en la misma dirección.
  • 1 -> 2, split : toma un solo hilo y envía dos copias en diferentes direcciones.
  • 1 -> 1, isZero? : consume el primer bit del hilo y lo envía en una de dos direcciones dependiendo de si el bit era 0 o 1.
  • 1 -> 1, EstaVacia? : consume toda la lista (es decir, la reemplaza con una lista vacía) y envía el hilo en una de dos direcciones, dependiendo de si la lista ya estaba vacía o no.

Con eso en mente, podemos encontrar una estrategia general. Usando concatenate queremos agregar repetidamente nuevos bits a una cadena que representa la entrada completa. Simplemente podemos hacer esto haciendo un bucle de la salida de la concatenación en una de sus entradas (e inicializamos esto en una lista vacía, borrando a {0}con isEmpty? ). La pregunta es cómo podemos terminar este proceso.

Además de agregar el bit actual, también antepondremos un 0 o 1 que indica si hemos alcanzado EOF. Si enviamos nuestra cadena a través de isZero? , eliminará ese bit nuevamente, pero distingamos el final de la secuencia, en cuyo caso simplemente dejamos que el hilo deje el borde de la cuadrícula (lo que hace que Ziim imprima el contenido del hilo en STDOUT y finalice el programa) .

¿Se puede determinar si hemos alcanzado EOF o no usando isEmpty? en una copia de la entrada.

Aquí está el diagrama que prometí:

              +----------------------------+   {0} --> isEmpty --> label <--+
              |                            |                    n    |      |
              v                            |                         v      |
    {0} --> label --> read --> split --> split ------------------> concat   |
                                 |                                   |      |
                           n     v     y                             |      |
 inv --> label --> concat <-- isEmpty --> concat <-- label <-- {0}   |      |
  ^        ^          |                     |          ^             |      |
  |        |          v                     v          |             |      |
 {0}       +------- split ---> label <--- split -------+             |      |
                                 |                                   |      |
                                 +-------------> concat <------------+      |
                                                   |                        |
                                              y    v                        |
                         print and terminate <-- isZero --------------------+

Algunas notas sobre dónde comenzar a leer:

  • La {0}esquina superior izquierda es el disparador inicial que inicia el bucle de entrada.
  • La {0}esquina superior derecha se borra inmediatamente a una lista vacía y representa la cadena inicial que gradualmente llenaremos con la entrada.
  • Los otros dos {0}s se introducen en un bucle "productor" (uno invertido, otro no), para darnos un suministro ilimitado de 0sy 1s que necesitamos anteponer a la cadena.

29
¿Cómo puedes incluso escribir un programa así sin que tu cerebro explote en un millón de pequeños trozos de tejido?
Ashwin Gupta

40

Hexagonía , 6 bytes.

Esto solía ser de 3 bytes (ver más abajo), pero esa versión ya no funciona desde la última actualización del idioma. Como nunca introduje intencionalmente el error que utilizaba la versión, decidí no contarlo.


Una solución sin errores (es decir, una que funciona con el intérprete fijo) resulta mucho más complicada. He tenido algunos problemas para incluirlo en una cuadrícula de 2x2, pero ahora encontré una solución, aunque necesito los 7 bytes completos :

<)@,;.(

Después de desplegarnos, obtenemos:

ingrese la descripción de la imagen aquí

Dado que el borde de memoria inicial es 0, <desvía incondicionalmente el puntero de instrucciones hacia la diagonal noreste, donde se ajusta al camino gris. El .es un no-op. Ahora ,lee un byte, lo )incrementa de tal manera que los bytes válidos (incluidos los bytes nulos) son positivos y EOF es 0.

Entonces, en EOF, la IP se ajusta a la ruta roja, donde @termina el programa. Pero si aún leemos un byte, entonces la IP se ajusta a la ruta verde, en lugar de eso, (disminuye el borde al valor original, antes de ;imprimirlo en STDOUT. La IP ahora vuelve incondicionalmente a la ruta gris, repitiendo el proceso.


Después de escribir un script de fuerza bruta para mi respuesta de Truth Machine, lo configuré para encontrar una solución de 6 bytes sin errores para el programa cat también. Sorprendentemente, encontró una: sí, exactamente una solución en todos los posibles programas de Hexagonía de 6 bytes. Después de las 50 soluciones de la máquina de la verdad, eso fue bastante sorprendente. Aquí está el código:

~/;,@~

Despliegue:

ingrese la descripción de la imagen aquí

El uso de ~(negación unaria) en lugar de ()es interesante, porque a) es un no-op en cero, b) intercambia los lados de la rama, c) en algunos códigos, un solo ~podría usarse dos veces para deshacer la operación consigo mismo . Así que aquí está lo que está pasando:

La primera vez (camino morado) que pasamos ~es un no-op. El /refleja la IP en la diagonal noroeste. La ruta gris ahora lee un carácter y multiplica su código de carácter por -1. Esto convierte el EOF ( -1) en un valor verdadero (positivo) y todos los caracteres válidos en valores falsos (no positivos). En el caso de EOF, la IP toma la ruta roja y el código termina. En el caso de un carácter válido, la IP toma el camino verde, donde ~deshace la negación e ;imprime el carácter. Repetir.


Finalmente, aquí está la versión de 3 bytes que solía funcionar en el intérprete original de Hexagony.

,;&

Al igual que la respuesta de Labyrinth, esto termina con un error si el flujo de entrada es finito.

Después de desplegar el código, corresponde a la siguiente cuadrícula hexadecimal:

ingrese la descripción de la imagen aquí

La .hay-ops. La ejecución comienza en el camino morado.

,lee un byte, ;escribe un byte. Luego, la ejecución continúa en el camino del salmón (¿ish?). Necesitamos &restablecer el borde de la memoria actual a cero, de modo que la IP salte nuevamente a la fila púrpura cuando toque la esquina al final de la segunda fila. Una vez ,que llegue a EOF, volverá -1, lo que provoca un error al ;intentar imprimirlo.


Diagramas generados con Timwi increíble 's HexagonyColorer .


2
La versión de 6 bytes es muy, muy inteligente. Los Brute-forcers pueden ser increíblemente increíbles.
ETHproductions

¿Tienes un enlace a tu fuerza bruta?
MD XF

@MDXF No guardo las distintas versiones, pero siempre es una modificación de este script Ruby .
Martin Ender

36

TeaScript , 0 bytes

TeaScript es un lenguaje de golf conciso compilado en JavaScript


En una actualización reciente, la entrada se agrega implícitamente como la primera propiedad.

Pruébalo en línea


Alternativamente, 1 byte

x

xcontiene la entrada en TeaScript. La salida es implícita


Estaba a punto de publicar esto :)
Kritixi Lithos

55
Ja, pensé que "Alternativamente" era un nombre de idioma ...
Quelklef

28

Brian y Chuck , 44 bytes

#{<{,+?+}_+{-?>}<?
_}>?>+<<<{>?_}>>.<+<+{<{?

Originalmente creé este lenguaje para Crear un lenguaje de programación que solo parece inutilizable . Sin embargo, resulta ser un ejercicio muy agradable para el golf.

Lo básico: cada una de las dos líneas define un programa similar a Brainfuck que opera en el código fuente del otro programa: el primer programa se llama Brian y el segundo se llama Chuck. Solo Brian puede leer y solo Chuck puede escribir. En lugar de los bucles de Brainfuck que tiene, ?que pasa el control al otro programa (y también cambian los roles del puntero de instrucción y el cabezal de la cinta). Es una adición a Brainfuck {y }escanea la cinta para la primera celda que no sea cero (o el extremo izquierdo). Además, _se reemplazan con bytes nulos.

Si bien no creo que esto sea óptimo todavía, estoy bastante contento con esta solución. Mi primer intento fue de 84 bytes, y después de varias sesiones de golf con Sp3000 (y tomando algo de inspiración de sus intentos), logré reducirlo lentamente a 44, unos pocos bytes a la vez. Especialmente el +}+truco brillante fue su idea (ver más abajo).

Explicación

La entrada se lee en la primera celda de la cinta de Chuck, luego se copia minuciosamente al final de la cinta de Brian, donde está impresa. Al copiarlo hasta el final, podemos guardar bytes al establecer el carácter anterior en cero.

El #es solo un marcador de posición, porque el control de conmutación no ejecuta la celda que activamos. {<{asegura que el cabezal de la cinta esté en la primera celda de Chuck. ,lee un byte de STDIN o -1si golpeamos EOF. Por lo tanto, incrementamos eso +para que sea cero para EOF y distinto de cero.

Asumamos por ahora que aún no estamos en EOF. Entonces la celda es positiva y ?cambiará el control a Chuck. }>mueve la cabeza de la cinta (en Brian) a +la _y ?pasa el control de nuevo a Brian.

{-ahora disminuye la primera celda de Chuck. Si aún no es cero, pasamos el control a Chuck nuevamente con ?. Esta vez }>mueve la cabeza de la cinta en Brian dos celdas a la derecha de la última celda distinta de cero. Inicialmente eso es aquí:

#{<{,+?+}_+{-?>}<?__
                   ^

Pero más adelante, ya tendremos algunos personajes allí. Por ejemplo, si ya hemos leído e impreso abc, se vería así:

#{<{,+?+}_+{-?>}<?11a11b11c__
                            ^

Donde los 1s son en realidad 1 bytes (veremos de qué se trata más adelante).

Esta celda siempre será cero, por lo que esta vez ? no cambiará el control. >mueve otra celda a la derecha e +incrementa esa celda. Esta es la razón por la cual el primer carácter en la entrada termina tres celdas a la derecha de la ?(y cada una de las siguientes tres celdas más a la derecha).

<<<retrocede al último carácter de esa lista (o ?si es el primer carácter) y {>vuelve a la +cinta de Brian para repetir el bucle, que transfiere lentamente la celda de entrada al final de la cinta de Brian.

Una vez que la celda de entrada esté vacía, el ?after {-ya no cambiará de control. Luego >}<mueve la cabeza de la cinta en Chuck hacia el _interruptor y cambia el control de modo que se ejecute la segunda mitad de Chuck.

}>>se mueve a la celda que hemos escrito más allá del final de la cinta de Brian, que es el byte que hemos leído de STDIN, por lo que lo imprimimos nuevamente .. Para }pasar este nuevo carácter en la cinta, necesitamos cerrar la brecha de dos bytes nulos, por lo que los incrementamos 1con <+<+(por eso hay 1 bytes entre los caracteres reales en la cinta final). Finalmente {<{vuelve al principio de la cinta de Brian y ?comienza todo desde el principio.

Quizás se pregunte qué sucede si el personaje que leemos era un byte nulo. En ese caso, la celda recién escrita sería en sí misma cero, pero dado que está al final de la cinta de Brian y no nos importa dónde está ese final, simplemente podemos ignorar eso. Eso significa que si la entrada fue ab\0de, entonces la cinta de Brian realmente terminaría luciendo así:

#{<{,+?+}_+{-?>}<?11a11b1111d11e

Finalmente, una vez que lleguemos a EOF, lo primero ?en la cinta de Brian será un no-op. En este punto terminamos el programa. La solución sería ingenuo para pasar a la final de la cinta y el interruptor de control de Chuck, de tal manera que los termiantes programa: >}>}<?. Aquí es donde la idea realmente inteligente de Sp3000 ahorra tres bytes:

+convierte la primera celda de Chuck en 1. Eso significa que }tiene un punto de partida y lo encuentra _en el medio de la cinta de Chuck. En lugar de saltarlo, simplemente cerramos la brecha convirtiéndolo en un 1con +también. Ahora veamos qué hace el resto del código de Brian con este Chuck modificado ...

{vuelve a la primera celda de Chuck como siempre, y la -convierte en un byte nulo. Eso significa que ?es un no-op. Pero ahora >}<, que usualmente mueve el cabezal de la cinta al centro de la cinta de Chuck, pasa al final de la cinta de Chuck y ?luego pasa el control a Chuck, terminando el código. Es agradable cuando las cosas simplemente funcionan ... :)


25

Haskell, 16 bytes

main=interact id

interactlee la entrada, la pasa a la función dada como argumento e imprime el resultado que recibe. ides la función de identidad, es decir, devuelve su entrada sin cambios. Gracias a la pereza de Haskell interactpuede funcionar con una entrada infinita.


23

sh + binutils, 3 2 bytes

dd

Bueno, no tan obvio. De @ Random832

Original:

cat

Lo dolorosamente obvio ...: D


12
Voy a hacer uno mejor: dd.
Random832

Iba a hacer gato ... D:
ev3commander

1
Sí, esto es genial y todo ... pero ¿170 representantes por escribir cat?
MD XF

1
@MDXF ¿qué pasa con quién sabe cuántas repeticiones de un segfault? ;)
caird coinheringaahing

23

Funciton , 16 bytes

╔═╗
╚╤╝

(Codificado como UTF-16 con una lista de materiales)

Explicación

El cuadro devuelve el contenido de STDIN. El extremo suelto lo emite.


19

Código de máquina Motorola MC14500B , 1.5 bytes

Escrito en hexadecimal:

18F

Escrito en binario:

0001 1000 1111

Explicación

1   Read from I/O pin
8   Output to I/O pin
F   Loop back to start

Los códigos de operación son de 4 bits cada uno.


1
-1 sin captura de pantalla, ejemplo o enlace de Try It Online: P (jk)
MD XF

2
+1. La única forma en que puedo pensar para optimizar esto aún más es soldar el pin de entrada al pin de salida y sacar el chip de su zócalo: P
Wossname

16

Mornington Crescent , 41 bytes

Take Northern Line to Mornington Crescent

No tengo idea de si Mornington Crescent puede manejar bytes nulos, y todas las entradas se leen antes de que comience el programa, ya que esa es la naturaleza del lenguaje.


15

Brainfuck, 5 bytes

,[.,]

Equivalente al pseudocódigo:

x = getchar()
while x != EOF:
    putchar(x)
    x = getchar()

Esto maneja flujos infinitos, pero trata los bytes nulos como EOF. El hecho de que BF pueda o no manejar bytes nulos correctamente varía de implementación en implementación, pero esto supone el enfoque más común.


1
¡MALDITO! ¡Me ganaste 5 minutos!
kirbyfan64sos

Si el primer carácter es NULL, esto no se ejecutará correctamente. ¿Entonces debería estar +[,.]bien?
Shelvacu

66
@Shel Esto está usando 0x00 como el byte EOF. Si el primer carácter es EOF, no imprime nada, funcionando como se esperaba.
Mego

2
"pseudocódigo" oh vamos, eso está claramente sin corchetes, sin punto y coma C: P
MD XF

14

Laberinto , 2 bytes

,.

Si el flujo es finito, esto terminará con un error, pero toda la salida producida por el error va a STDERR, por lo que el flujo de salida estándar es correcto.

Como en Brainfuck, ,lee un byte (empujándolo a la pila principal de Labyrinth) y .escribe un byte (sacándolo de la pila principal de Labyrinth).

La razón de este bucle es que ambos ,y .son "callejones sin salida" en el laberinto (muy trivial) representado por el código fuente, de modo que el puntero de instrucción simplemente gira en el lugar y vuelve al otro comando.

Cuando presionamos EOF ,empuja en su -1lugar y .arroja un error porque -1no es un código de carácter válido. Esto podría cambiar en el futuro, pero aún no lo he decidido.


Como referencia, podemos resolver esto sin un error en 6 bytes de la siguiente manera

,)@
.(

Aquí, )aumenta el byte que leemos, lo que da 0en EOF y algo positivo de lo contrario. Si el valor es 0, la IP se mueve directamente, presionando el botón @que finaliza el programa. Si el valor fue positivo, la IP en cambio girará a la derecha hacia la (que disminuye la parte superior de la pila a su valor original. El IP ahora está en una esquina y simplemente seguirá girando a la derecha, imprimiendo con ., leyendo un nuevo byte con ., antes de que llegue a la bifurcación de )nuevo.


13

C, 40 bytes

main(i){while(i=~getchar())putchar(~i);}

main () {while (255-putchar (getchar ()));} es un par de bytes más corto.
Alchymist

1
Lamentablemente, eso sale prematuramente en bytes 0xFF y agrega un byte 0xFF a la entrada si no lo contiene.
Dennis

¿Qué pasa con lo siguiente, 36 bytes: main () {for (;; putchar (getchar ()));};
Johan du Toit

@ user2943932 Cuando llega a EOF, getchardevuelve -1 , por lo que su código imprimirá una secuencia infinita de 0xFF bytes después de la entrada (finita).
Dennis

12

> <> , 7 bytes

i:0(?;o

Probarlo aquí . Explicación:

i:0(?;o
i        Take a character from input, pushing -1 if the input is empty
 :0(     Check if the input is less than 0, pushing 1 if true, 0 if false
    ?;   Pop a value of the top of the stack, ending the program if the value is non-zero
      o  Otherwise, output then loop around to the left and repeat

Si desea que continúe hasta que le dé más información, reemplace ;con !.


Aww hombre, esperaba publicar la respuesta> <> ...: P (+1!)
El'endia Starman

1
io(2 bytes) hace lo mismo, pero se bloquea y escribe something smells fishy...en STDERR al final de la ejecución, lo cual está permitido.
Lynn

@Mauris, el intérprete en línea solo genera bytes nulos en lugar de terminar con un error.
DanTheMan

11

Conjunto X86, 70 bytes

Desmontaje con objdump:

00000000 <.data>:
   0:   66 83 ec 01             sub    sp,0x1
   4:   66 b8 03 00             mov    ax,0x3
   8:   00 00                   add    BYTE PTR [eax],al
   a:   66 31 db                xor    bx,bx
   d:   66 67 8d 4c 24          lea    cx,[si+0x24]
  12:   ff 66 ba                jmp    DWORD PTR [esi-0x46]
  15:   01 00                   add    DWORD PTR [eax],eax
  17:   00 00                   add    BYTE PTR [eax],al
  19:   cd 80                   int    0x80
  1b:   66 48                   dec    ax
  1d:   78 1c                   js     0x3b
  1f:   66 b8 04 00             mov    ax,0x4
  23:   00 00                   add    BYTE PTR [eax],al
  25:   66 bb 01 00             mov    bx,0x1
  29:   00 00                   add    BYTE PTR [eax],al
  2b:   66 67 8d 4c 24          lea    cx,[si+0x24]
  30:   ff 66 ba                jmp    DWORD PTR [esi-0x46]
  33:   01 00                   add    DWORD PTR [eax],eax
  35:   00 00                   add    BYTE PTR [eax],al
  37:   cd 80                   int    0x80
  39:   eb c9                   jmp    0x4
  3b:   66 b8 01 00             mov    ax,0x1
  3f:   00 00                   add    BYTE PTR [eax],al
  41:   66 31 db                xor    bx,bx
  44:   cd 80                   int    0x80

La fuente:

sub esp, 1
t:
mov eax,3
xor ebx,ebx
lea ecx,[esp-1]
mov edx,1
int 0x80
dec eax
js e
mov eax,4
mov ebx,1
lea ecx,[esp-1]
mov edx,1
int 0x80
jmp t
e:
mov eax,1
xor ebx,ebx
int 0x80

1
Entonces, lo objdumpdesmontó como código de 32 bits, mientras que parece haber compilado como 16 bits. Que creer Desde su uso int 0x80, supongo que está destinado a Linux, pero ¿por qué compilar como 16 bits?
Ruslan

@Ruslan que no se dan cuenta de que fue compilado en 16 bits ...
kirbyfan64sos

11

Lambda universal , 1 byte

!

Un programa Universal Lambda es una codificación de un término lambda en binario, cortado en trozos de 8 bits, rellenando fragmentos incompletos con cualquier bit, convertido en un flujo de bytes.

Los bits se traducen a un término lambda de la siguiente manera:

  • 00 introduce una abstracción lambda.
  • 01 representa una aplicación de dos términos posteriores.
  • 111..10, Con n repeticiones de la broca 1, se refiere a la variable de la n º lambda padre; es decir, es un índice de De Bruijn en unario.

Por esta conversión, 0010es la función de identidad λa.a, lo que significa que cualquier programa de un solo byte del formulario 0010xxxxes un catprograma.


1
Pero !es que 0x21no 0x4_?
wchargin

Fijo. --------
Lynn

10

PowerShell, 88 41 30 bytes

$input;write-host(read-host)-n

EDITAR: olvidé que puedo usar la $inputvariable automática para la entrada de la tubería ... EDIT2: no es necesario probar la existencia de$input

Sí, entonces ... STDIN en PowerShell es ... raro, digamos. Con el supuesto de que necesitamos aceptar aportes de todos los tipos de STDIN, esta es una posible respuesta a este catálogo, y estoy seguro de que hay otros. 1

Sin embargo, la entrada de canalización en PowerShell no funciona como se podría pensar. Dado que las tuberías de PowerShell es una función de la lengua, y no una función del medio ambiente / shell (y PowerShell no es exclusivamente un lenguaje de todos modos), hay algunas peculiaridades en el comportamiento.

Para empezar, y lo más relevante para esta entrada, la tubería no se evalúa instantáneamente (la mayoría de las veces). Es decir, si tenemos command1 | command2 | command3en nuestro shell, command2no tomaremos información o comenzará el procesamiento hasta que se command1complete ... a menos que encapsule su command1con ForEach-Object... que es diferente a ForEach. (aunque ForEaches un alias para ForEach-Object, pero ese es un tema separado, ya que estoy hablando ForEachcomo la declaración, no alias)

Esto significaría que algo así yes | .\simple-cat-program.ps1(aunque yesrealmente no existe, pero lo que sea) no funcionaría porque yesnunca se completaría. Si pudiéramos hacer ForEach-Object -InputObject(yes) | .\simple-cat-program.ps1eso debería (en teoría) funcionar.

Conociendo ForEach y ForEach-Object en Microsoft "¡Hola, Scripting Guy!" Blog.

Entonces, todos esos párrafos explican por qué if($input){$input}existe. Tomamos un parámetro de entrada que se crea especialmente automáticamente si la entrada de la tubería está presente, probamos si existe y, de ser así, la enviamos.

Luego, tomamos información del usuario a (read-host)través de lo que es esencialmente una secuencia STDIN separada, y la retiramos write-host, con la -nbandera (abreviatura de -NoNewLine). Tenga en cuenta que esto no admite la entrada de longitud arbitraria, ya read-hostque solo se completará cuando se ingresa un salto de línea (técnicamente cuando el usuario presiona "Enter", pero funcionalmente equivalente).

Uf.

1 Pero hay otras opciones:

Por ejemplo, si nos preocupamos solo por la entrada de la tubería, y no requerimos un programa completo, podría hacer algo como | $_lo que simplemente generaría lo que fuera entrada. (En general, eso es algo redundante, ya que PowerShell tiene una salida implícita de cosas "dejadas atrás" después de los cálculos, pero eso es algo aparte).

Si solo nos interesa la entrada interactiva del usuario, podríamos usar solo write-host(read-host)-n.

Además, esta función tiene la característica peculiar de aceptar entradas de línea de comandos, por ejemplo .\simple-cat-program.ps1 "test", llenaría (y luego generaría) la $avariable.


¡no olvides tus alias integrados!
Chad Baxter

10

Cubix , 6 5 bytes

¡Ahora maneja bytes nulos!

@_i?o

Cubix es un esolang bidimensional basado en pila. Cubix es diferente de otros idiomas 2D en que el código fuente está envuelto alrededor del exterior de un cubo.

¡Pruébalo en línea! Nota: hay un retraso de 50 ms entre iteraciones.

Explicación

Lo primero que hace el intérprete es averiguar el cubo más pequeño en el que se ajustará el código. En este caso, la longitud del borde es 1. Luego, el código se rellena sin operaciones .hasta que se llenen los seis lados. El espacio en blanco se elimina antes del procesamiento, por lo que este código es idéntico al anterior:

  @
_ i ? o
  .

Ahora se ejecuta el código. El IP (puntero de instrucción) comienza en el extremo izquierdo, apuntando hacia el este.

El primer carácter que encuentra la IP es _, que es un espejo que da vuelta a la IP si está orientada al norte o al sur; actualmente está orientado al este, por lo que esto no hace nada. El siguiente es i, que ingresa un byte desde STDIN. ?gira la IP hacia la izquierda si el elemento superior es negativo, o hacia la derecha si es positivo. Hay tres caminos posibles aquí:

  • Si el byte ingresado es -1 (EOF), la IP gira a la izquierda y golpea @, lo que finaliza el programa.
  • Si el byte ingresado es 0 (byte nulo), la IP simplemente continúa recta, generando el byte con o.
  • De lo contrario, la IP gira a la derecha, viaja a través de la cara inferior y golpea el espejo _. Esto lo da vuelta, enviándolo de vuelta al ?, que lo vuelve a girar a la derecha y genera el byte.

Creo que este programa es óptimo. Antes de que Cubix pudiera manejar bytes nulos (EOF era 0, no -1), este programa funcionó para todo menos bytes nulos:

.i!@o

He escrito una fuerza bruta para encontrar todos los programas de gato de 5 bytes. Aunque tarda unos 5 minutos en terminar, la última versión ha encontrado 5 programas:

@_i?o   (works as expected)
@i?o_   (works in exactly the same way as the above)
iW?@o   (works as expected)
?i^o@   (false positive; prints U+FFFF forever on empty input)
?iWo@   (works as expected)

No edites una docena de publicaciones a la vez. Estás inundando la portada. 3 a la vez no es un problema, pero si tiene que hacer más que eso, haga sus ediciones en pequeños lotes cada 12 horas más o menos.
Martin Ender

@MartinEnder Lo siento, acabo de notar eso. Los espaciaré en el futuro.
ETHproductions

9

Vitsy, 2 bytes

zZ

zobtiene toda la pila de entrada y la empuja a la pila del programa activo. Zimprime toda la pila activa en STDOUT.

Metodo alternativo:

I \ il \ O
Repito el siguiente carácter para la longitud de la pila de entrada.
  Agarro un elemento de la entrada.
   l \ Repita el siguiente carácter para la longitud de la pila de programas actualmente activa.
     O Muestra el elemento superior de la pila como un personaje.

2
^ _ ^ ¡Ten un +1 de todos modos! :)
El'endia Starman

¡Qué pena, mi favorito!
Addison Crump

¿Por qué los votos negativos? Esta parece ser una entrada perfectamente válida
Conor O'Brien el

1
Que es válida por todas las características.
Addison Crump

9

MarioLANG , 11 bytes

,<
."
>!
=#

No estoy completamente seguro de que esto sea óptimo, pero es el más corto que encontré.

Esto admite flujos infinitos y terminará con un error al llegar a EOF (al menos la implementación de referencia de Ruby lo hace).

Hay otra versión de esto que convierte a Mario en un ninja que puede hacer doble salto:

,<
.^
>^
==

En cualquier caso, Mario comienza a caer por la columna izquierda, donde ,lee un byte y .escribe un byte (que arroja un error en EOF porque ,no devuelve un carácter válido). >asegura que Mario camina hacia la derecha ( =es solo un terreno para caminar). Luego se mueve hacia arriba, ya sea a través de un salto doble con ^un elevador ( "y el #par) antes de que <le diga que vuelva a la columna de la izquierda.


8

rs , 0 bytes


Seriamente. rs solo imprime lo que se obtiene si el script dado está completamente vacío.


7

GolfScript, 3 bytes

:n;

El programa vacío hace eco de la entrada estándar. El lenguaje no puede manejar secuencias infinitas. Sin embargo, agrega una nueva línea, como mencionó @Dennis. Lo hace envolviendo toda la pila en una matriz y llamando puts, que se define como print n print, donde nhay una nueva línea. Sin embargo, podemos redefinir npara ser STDIN y luego vaciar la pila, que es precisamente lo que :n;hace.


7

Coche medio roto en tráfico pesado , 9 + 3 = 12 bytes

#<
o^<
 v

Half-Broken Car in Heavy Traffic (HBCHT) toma la entrada como argumentos de línea de comando, así que corre como

py -3 hbcht cat.hbc -s "candy corn"

Tenga en cuenta que el +3 es para la -sbandera, que sale como caracteres. Además, HBCHT no parece manejar NUL, ya que todos los ceros se eliminan de la salida (por ejemplo, 97 0 98se emite como dos caracteres ab).

Explicación

En HBCHT, su automóvil comienza en la oy su objetivo es la salida #. ^>v<dirija el movimiento del automóvil, mientras modifica simultáneamente una cinta tipo BF ( ^>v<traduzca a +>-<). Sin embargo, como sugiere el nombre del idioma, su automóvil solo puede girar a la derecha; cualquier intento de girar a la izquierda se ignora por completo (incluidos sus efectos de memoria). Tenga en cuenta que esto es solo para girar: su automóvil es perfectamente capaz de avanzar / retroceder.

Otras partes interesantes sobre HBCHT son que la dirección inicial de su automóvil es aleatoria y la cuadrícula es toroidal. Por lo tanto, solo necesitamos que el automóvil llegue a la salida sin modificar la cinta para las cuatro direcciones iniciales:

  • Arriba y abajo son sencillos y se dirigen directamente a la salida.

  • A la izquierda, ajustamos y ejecutamos <e incrementamos con ^. No podemos girar a la izquierda en el siguiente, <así que ajustamos y decrementamos v, negando el incremento anterior. Como nos dirigimos hacia abajo ahora podemos girar a la derecha en <y salir, después de haber movido el puntero dos veces y no modificar los valores de las celdas.

  • Para la derecha, hacemos lo mismo que la izquierda, pero omitimos la primera ^ya que no podemos girar a la izquierda.


Editar : Resulta que el intérprete HBCHT le permite ejecutar solo una ruta a través de un indicador de línea de comando, por ejemplo

py -3 hbcht -d left cat.hbc

Sin embargo, no solo el indicador es demasiado costoso para esta pregunta en particular (al menos 5 bytes " -d u"), parece que todas las rutas aún deben poder llegar a la salida para que el código se ejecute.


7

Minkolang , 5 bytes

od?.O

Pruébalo aquí

Explicación

olee un carácter de la entrada y empuja su código ASCII a la pila ( 0si la entrada está vacía). dluego duplica la parte superior de la pila (el carácter que se acaba de leer). ?es un trampolín condicional, que salta la siguiente instrucción de la parte superior de la pila no lo es 0. Si la entrada estaba vacía, entonces .no se salta y el programa se detiene. De lo contrario, Ogenera la parte superior de la pila como un personaje. La naturaleza toroidal de Minkolang significa que esto gira hasta el principio.


2
Grar! ¡Golpeaste mi idioma! ¡INACEPTABLE! +1
Addison Crump

7

INTERCALL , 133 bytes

wat

INTERCALL IS A ANTIGOLFING LANGUAGE
SO THIS HEADER IS HERE TO PREVENT GOLFING IN INTERCALL
THE PROGRAM STARTS HERE:
READ
PRINT
GOTO I

Parece que alguien realmente jugó al golf en un lenguaje puramente anti-golf ... 133-116 = 17
Erik the Outgolfer

@ EʀɪᴋᴛʜᴇGᴏʟғᴇʀ Dado que el programa cat es bastante simple, este no es el caso de todos los programas ... codegolf.stackexchange.com/a/82748/53745
TuxCrafting

La persona que hizo el idioma tenía la intención de usar números romanos, pero si fuera el caso para imprimir 500(no estoy seguro), sería PRINT D, ¿verdad? (excluyendo el encabezado)
Erik the Outgolfer

@ EʀɪᴋᴛʜᴇGᴏʟғᴇʀ No, INTERCALL solo puede imprimir caracteres ASCII y usar una pila, por ejemplo, para imprimir el caracter con un valor ascii 20, el código es PUSH XX<newline>PRINTo PUSH XX AND PRINT. Ah, y yo soy el creador de INTERCALL
TuxCrafting

7

V , 0 bytes

Pruébalo en línea!

La idea de V de "memoria" es solo una gigantesca matriz 2D de personajes. Antes de ejecutar cualquier programa, toda la entrada se carga en esta matriz (conocida como "The Buffer"). Luego, al final de cualquier programa, se imprime todo el texto en el búfer.

En otras palabras, el programa vacío es un programa cat.


6

Muñeco de nieve 1.0.2 , 15 caracteres

(:vGsP10wRsp;bD

Tomado directamente del examplesdirectorio de Snowman . Lee una línea, imprime una línea, lee una línea, imprime una línea ...

Tenga en cuenta que debido a un detalle de implementación, cuando STDIN está vacío, vgdevolverá lo mismo que lo haría para una línea vacía. Por lo tanto, esto imprimirá repetidamente nuevas líneas en un bucle infinito una vez que STDIN esté cerrado. Esto puede corregirse en una versión futura.

Explicación del código:

(        // set two variables (a and f) to active—this is all we need
:...;bD  // a "do-loop" which continues looping as long as its "return value"
         // is truthy
  vGsP   // read a line, print the line
  10wRsp // print a newline—"print" is called in nonconsuming mode; therefore,
         // that same newline will actually end up being the "return value" from
         // the do-loop, causing it to loop infinitely


5

Fisión , 4 bytes.

R?J!

¿No es agradable cuando superas los programas de muestra en el repositorio del lenguaje? :) Como referencia, tiene la solución de 7 bytes

R?J0;0!

Explicación

Entonces, Rcomienza el flujo de control con un átomo que va hacia la derecha. ?lee un personaje de STDIN en la masa del átomo. Mientras estemos leyendo personajes, la energía permanece en cero, por lo que el Járbitro no funciona y !imprime el personaje. El átomo regresa al inicio ( Rahora no funciona) y repite todo el proceso.

Cuando presionamos EOF, ?estableceremos la energía del átomo en 1, por lo que el Járbitro ahora omitirá el comando de impresión. Pero cuando un átomo golpea ? después de que EOF ya ha sido devuelto, destruirá el átomo en su lugar, lo que termina el programa.

(La solución del autor del lenguaje utiliza un explícito ;para finalizar el programa, que de lo 0contrario se omite con dos portales).


5

Shtriped , 20 bytes

e )
"
 r )
 s )
 "
"

Esto demuestra descaradamente que casi cualquier cadena ASCII imprimible es un identificador válido en Shtriped.

Cómo funciona:

e )   \ declares a variable named )
"     \ defines a function with 0 arguments named "
 r )  \ gets a line of string input, saving it to )
 s )  \ prints ) as a string
 "    \ recursively calls ", effectively looping forever
"     \ calls " from the main scope to get things started

No hay una forma real de detectar EOF, por lo que esto se repite para siempre como la respuesta de Python .

Sin embargo, puede detenerlo fácilmente cuando se proporciona una línea vacía (30 bytes):

e )
"
 r )
 d ) \ tries to decrement ), if it was the empty string, aka 0, it can't, so 0 is returned all the way up
 i ) \ increment ) to put it back to normal after possibly decrementing
 s )
 "
"

Tenga en cuenta que Shtriped I / O solo admite ASCII imprimible , pestañas, línea, retornos de carro, pestañas verticales y alimentaciones de formularios (100 caracteres en total). Esto se debe a que internamente, las cadenas se representan como enteros de precisión arbitraria no negativa, y debe haber un alfabeto finito de caracteres para poder codificar todas las cadenas.

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.