Las teselas duodádicas son tipos de bloques de función cuadrados que toman dos entradas, una desde su lado superior y otra desde su lado izquierdo, y tienen dos salidas, una en su lado derecho y otra en su lado inferior. Cada una de sus salidas es una función separada de sus dos entradas.
Por ejemplo, si #
representa un mosaico genérico, la salida derecha R
es una función f
de entradas T
y L
, y la salida inferior B
es otra función g
de T
y L
:
T
L#R R = f(T, L)
B B = g(T, L)
(Los mosaicos se denominan "dúo" ya que hay dos funciones y "diádico" ya que ambas funciones tienen dos argumentos ).
Los mosaicos se pueden componer juntos en una cuadrícula, las salidas de un mosaico van directamente a las entradas de los mosaicos vecinos. Aquí, por ejemplo, la salida derecha de la izquierda #
entra en la entrada izquierda de la derecha #
:
AB D = f(f(A, C), B)
C##D E = g(A, C)
EF F = g(f(A, C), B)
Puede imaginar que, dado un conjunto de mosaicos duodádicos, cada uno con una funcionalidad específica, se podrían hacer composiciones complejas (y potencialmente útiles).
En este desafío, solo nos ocuparemos del conjunto tradicional de diez mosaicos duodádicos basados en lógica , donde todas las entradas y salidas son números binarios de un solo bit (ceros o unos). Usaremos un carácter ASCII separado para denotar cada tipo de mosaico.
Los caracteres de mosaico y sus relaciones de entrada-salida son los siguientes:
( T
es para la entrada superior, L
para la entrada izquierda, R
para la salida derecha, B
para la salida inferior).
- Cero:
0
o(espacio) →
R = 0
,B = 0
- Uno:
1
→R = 1
,B = 1
- Cruz:
+
→R = L
,B = T
- Espejo:
\
→R = T
,B = L
- Solo superior:
U
→R = T
,B = T
- Solo izquierda:
)
→R = L
,B = L
- No:
!
→R = not L
,B = not T
- Y:
&
→R = L and T
,B = L and T
- O:
|
→R = L or T
,B = L or T
- Xor:
^
→R = L xor T
,B = L xor T
Reto
Escriba un programa o función que tome en una cuadrícula rectangular de los caracteres 0 1+\U)!&|^
que representa un "circuito" hecho usando los diez mosaicos duodádicos basados en lógica. También necesita tomar dos cadenas de 0
'sy 1
' s; una será la columna de entrada izquierda y la otra será la fila de entrada superior. Su programa / función necesita imprimir / devolver la fila de salida inferior y la columna de salida derecha (también en 0
'sy 1
' s).
Por ejemplo, en esta cuadrícula
+++
+++
todas las entradas fluyen directamente a través de la cuadrícula a las salidas
ABC
D+++D
E+++E
ABC
entonces una entrada de 010
/ 01
tendría salida 010
/ 01
:
010
0+++0
1+++1
010
El resultado exacto de su programa sería [bottom output row]\n[right output column]
o [bottom output row]/[right output column]
:
010
01
o
010/01
Si escribió una función, podría devolver las dos cadenas en una tupla o lista (o aún imprimirlas).
Detalles
- Tome las tres entradas como cadenas de cualquier manera razonable (preferiblemente en la cuadrícula de orden, fila superior, columna izquierda): línea de comando, archivo de texto, sdtin, función arg.
- Puede suponer que las longitudes de fila y columna de entrada coincidirán con las dimensiones de la cuadrícula y solo contendrán
0
'sy1
' s. - Su cuadrícula debe usar los caracteres adecuados (
0 1+\U)!&|^
). Recuerda eso0
ysignifica lo mismo.
Casos de prueba
(Lea E / S como top
/ left
→ bottom
/ right
.)
Nand:
&!
00
/ 0
→ 01
/ 1
00
/ 1
→ 01
/ 1
10
/ 0
→ 01
/ 1
10
/ 1
→ 11
/0
Todos unos:
1111
1\+\
1+\+
1\+\
Cualquier entrada debe resultar en 1111
/ 1111
.
Xor de Nand: (observe la columna de espacios finales)
\)+\
U&!&
+! !
\&!&
!
00000
/ 00000
→ 00000
/ 00000
00000
/ 10000
→ 00010
/ 00000
10000
/ 00000
→ 00010
/ 00000
10000
/ 10000
→ 00000
/00000
Zig zag:
+++\00000000
000\!!!!\000
00000000\+++
El primer bit de la entrada izquierda se convierte en el último bit de la salida derecha. Todo lo demás es 0
.
000000000000
/ 000
→ 000000000000
/ 000
000000000000
/ 100
→ 000000000000
/001
Propagación:
)))
UUU
U+U
U+U
UUU
El primer bit de la entrada izquierda va a todas las salidas.
000
/ 00000
→ 000
/ 00000
000
/ 10000
→ 111
/11111
Aquí hay un pastebin de todos los casos de prueba de cuadrícula 1 × 1.
Tanteo
La presentación más corta en bytes gana.
Bonus: ¿Qué "circuitos" geniales puedes hacer?
PD: No te molestes en buscar en Google "baldosas duodádicas". Los inventé ayer; D
Si quieres discutir expandir esta idea a un lenguaje de programación completo, ven a esta sala de chat .
fuente
Respuestas:
Pyth, 122
Como un monstruo. Utiliza simplemente recursividad, nada lujoso como la programación dinámica.
Demostración en línea .
La entrada es de la siguiente manera: primero la cuadrícula (sin escape, sin símbolos adicionales) y luego las dos líneas de entrada, por ejemplo (Zig zag)
fuente
Mathematica,
331276270267264262252250 bytesEl
es un carácter Unicode de uso privado que Mathematica usa como superíndiceT
, es decir, es el operador de transposición.Aquí hay una versión más legible:
Esta es una función sin nombre que toma las tres cadenas para las entradas de cuadrícula, superior e izquierda e imprime las salidas inferior y derecha.
Explicación
Veamos este paso a paso (intentaré no asumir ningún conocimiento de Mathematica). Es necesario leer el código de frente a frente. El algoritmo básico simplemente recorre las líneas que computan cada función y almacenan los resultados
f
para que sean accedidos por mosaicos posteriores.Procesamiento de entrada
Esa es esta parte:
Esto simplemente divide la cuadrícula en una lista anidada de caracteres (tenga en cuenta que definí
h
como un alias paraCharacter
algún lugar del código) y luego antepone una fila y una columna con las entradas. Esto funciona, porque1
y0
también son los nombres de los mosaicos de función constante, por lo que colocarlos en ellos tiene el mismo efecto que alimentar las entradas manualmente. Dado que estas son funciones, técnicamente tomarán su entrada desde fuera de la cuadrícula, pero dado que son funciones constantes, eso no importa. La esquina superior izquierda obtiene un,0
pero esto es bastante arbitrario ya que los resultados de ese mosaico nunca se utilizan.También tenga en cuenta la transposición. Agregar columnas requiere más caracteres que agregar filas, por lo que transpongo la cuadrícula después de agregar la fila superior. Esto significa que las partes superior / inferior e izquierda / derecha se intercambian por la parte principal del programa, pero son completamente intercambiables, por lo que no importa. Solo necesito asegurarme de devolver los resultados en el orden correcto.
Resolviendo la cuadrícula
(Esta sección está un poco desactualizada. Se solucionará una vez que esté realmente seguro de que he terminado de jugar al golf).
A continuación, corremos
MapIndexed
sobre el nivel interno de esta lista anidada. Esto llama a la función anónima proporcionada como primer argumento para cada carácter en la cuadrícula, y también le da una lista con las dos coordenadas actuales. La cuadrícula se atraviesa en orden, por lo que podemos calcular con seguridad cada celda en función de las anteriores.Utilizamos las variables
r
(ight) yb
(ottom) como tablas de búsqueda para los resultados de cada celda. Nuestra función anónima tiene las coordenadas actuales#2
, por lo que obtenemos las entradas a cualquier celda conTenga en cuenta que en la primera fila y columna esto accederá a valores indefinidos de
r
yb
. Mathematica realmente no tiene un problema con eso y solo le devolverá sus coordenadas, pero descartamos este resultado de todos modos, ya que todos los mosaicos en esa fila / columna son funciones constantes.Ahora esta cosa:
Es una forma de golf de
Lo que a su vez es una función que, dadas las dos entradas de mosaico, devuelve una Asociación (lo llamaría un hashmap o una tabla en otros idiomas), que contiene todos los resultados de mosaico posibles para estas dos entradas. Para comprender cómo se implementan todas las funciones, debe saber que se puede acceder al primer argumento de dicha función
#
y al segundo con#2
. Además,##
le ofrece una secuencia de ambos argumentos que se pueden usar para "salpicar" los argumentos.0
: es sencillo, solo devolvemos una constante{0, 0}
y también la asignamosz
para uso futuro (por ejemplo, en el mosaico de espacios).1
: es esencialmente justo{1,1}
, pero tenerz
esto se acorta a1+z
. También guardamos estoo
, porque será útil para todos los mosaicos donde ambas salidas son idénticas.+
: Aquí hacemos uso de la secuencia.{##}
es igual{#,#2}
y pasa ambas entradas sin cambios.\
: Intercambiamos los dos argumentos,{#2,#}
.U
: Ahora podemos hacer uso deo
.o#2
significa{1,1}*#2
que solo ponemos el argumento superior en ambas salidas.)
Análogamente para el argumento de la izquierda:o#
.!
: Bit a bit no es molesto en Mathematica, pero ya que sólo tenga0
y1
, simplemente puede restar las dos entradas de1
(por lo tanto la inversión de ellos) y pasarlas:1-{##}
.&
: Este es bastante ingenioso. Primero notamos que bit a bit y para0
y1
es idéntico a la multiplicación. Además,o##
es lo mismo queo*#*#2
.|
: De nuevo, usamos una función equivalente. Bitwise o es lo mismo queMax
en este caso, por lo que aplicamosMax
a los argumentos de entrada y multiplicamos el resultado en{1,1}
.^
: Lo más corto que he encontrado para xor es tomar la diferencia y cuadrarla (para asegurar la positividad), así que tenemoso(#-#2)^2
.Una vez que esta función se completa y devuelve la asociación completa, usamos el carácter de la celda actual para extraer el elemento que nos interesa y almacenarlo en
r
yb
. Tenga en cuenta que este también es el valor de retorno de la función anónima utilizadaMapIndexed
, por lo que la asignación en realidad me dará una cuadrícula de todos los resultados.Procesamiento de salida
MapIndexed
devuelve una cuadrícula 3D, donde la primera dimensión corresponde a la coordenada de la cuadrícula horizontal (recuerde la transposición anterior), la segunda dimensión corresponde a la coordenada de la cuadrícula vertical y la tercera indica si tenemos una salida inferior o izquierda. Tenga en cuenta que esto también contiene la fila y la columna de entrada de las que debemos deshacernos. Entonces accedemos a la salida inferior de la fila inferior cony la salida derecha de la columna final con
Tenga en cuenta que
2;;
es un rango del segundo al último elemento.Por último, aplicamos
Print
a ambos (utilizando@@@
como el azúcar sintáctico para el segundo nivelApply
), que solo imprime todos sus argumentos de forma consecutiva (y dado que se aplica a dos expresiones separadas, habrá una nueva línea entre el fondo y salida correcta).fuente
C,
332309272270266259247225 bytesVer resultados en línea aquí!
Esto define una función
void f(char*, char*, char*)
, que debe tomar el tablero como su primera entrada, luego la fila superior de entrada y luego la fila izquierda de entrada.Esto es lo que solía probar:
Por lo tanto, al ingresar el multiplicador de 2 bits de Sp3000:
Obtenemos:
En otra nota, con el medio sumador de Sp3000 en mente, me gustaría ver un sumador completo ... ¡Uno de ustedes lo hizo! No creo que el sistema sea un lenguaje de programación, pero ha sido muy interesante. ¡Sin embargo, este parece ser un excelente objetivo para metagolf!Una breve explicación:
Aquí está el código desvelado y comentado:
Repetimos
c
, de izquierda a derecha (luego de arriba a abajo), reescribiendo last
entradas cada vez y sacando una salida de la derecha que se inserta en lal
cadena. Podemos imaginar esto como reemplazar la fila superior dec
con1
'sy0
' s iterativamente, y hacer un seguimiento de los bits que se expulsan a la derecha.Aquí hay una secuencia más visual, fila por fila:
Obviamente, esto se vuelve más complicado con diferentes símbolos y tamaños, pero la idea central es válida. Esto funciona solo porque los datos nunca fluyen hacia arriba o hacia la izquierda.
fuente
f
af(c,t,l)char*c,*t,*l
(no le importa una mierda el tipo de retorno).f(c,t,l)char*c,*t,*l;
. No compile en modo C11, ya que la regla int implícita que nos permite eliminar el tipo de retorno se ha eliminado en esa revisión.*l
? Se compila en modo C99 en mi máquina.Python 2, 316 bytes
Esta función construye 10 funciones lambda de mosaico, luego itera a través de la cuadrícula, actualizando los estados lógicos. Luego se imprimen los estados lógicos verticales y horizontales finales.
El código no protegido que incluye pruebas:
El
test.txt
archivo (incluidas otras 2 pruebas de Sp3000):La salida de prueba:
fuente
Python 2,
384338325 bytesEn serio CH, si esto no es un juguete ya deberías comenzar a llamar a algunas fábricas de juguetes.
Más golf y mucho menos eficiente ahora, pero aún no ha alcanzado a CarpetPython. Entrada como
f("1111\n1\\+\\\n1+\\+\n1\\+\\","0101","1010")
, salida es una tupla de dos cadenas. Sin embargo, asegúrese de que el tablero no tenga una nueva línea final, lo que romperá las cosas.Programa de prueba
También puede probar todos los casos posibles con
test_all()
.Casos de prueba extra
Media víbora
Aquí hay un medio sumador que agrega los bits superiores izquierdos, generando
<input bit> <carry> <sum>
:Pruebas:
La salida debe ser la misma incluso si se cambian los bits segundo / tercero de las entradas.
Giro a la derecha
Dado
abc / def
, esto producefab / cde
:Pruebas:
Clasificador de 3 bits
Ordena los primeros tres bits de la parte superior en los últimos tres bits de la parte inferior. La salida correcta es basura.
Pruebas:
Multiplicador de 2 bits por 2 bits
Toma los bits 1º / 2º de la parte superior como el primer número y los bits 3º / 4º de la parte superior como el segundo número. Salidas a los últimos cuatro bits de fondo. La salida correcta es basura.
Editar: Golfed una columna y dos filas.
Pruebas:
fuente
R,
524517Probablemente hay mucho espacio para reducir esto en este momento, pero esto ha sido realmente interesante de hacer. Hay dos funciones La función d es el trabajador yf es el comparador.
La función d se llama con 3 cadenas, puertas, superior e izquierda. Las puertas se colocan en una matriz determinada por el ancho.
Formateado un poco
Algunas pruebas
fuente