Cadenas Gozinta
(Inspirado por el Proyecto Euler # 606 )
Una cadena de gozinta para n es una secuencia {1,a,b,...,n}
en la que cada elemento divide adecuadamente al siguiente. Por ejemplo, hay ocho cadenas de gozinta distintas para 12:
{1,12}, {1,2,12}, {1,2,4,12}, {1,2,6,12}, {1,3,12}, {1,3,6,12}, {1,4,12} and {1,6,12}.
El reto
Escriba un programa o función que acepte un entero positivo ( n > 1
) y genere o devuelva todas las cadenas de gozinta distintas para el número dado.
- El orden en las cadenas importa (ascendente), el orden de las cadenas no.
- En el caso de que exista una posibilidad remota, no puede usar un dispositivo incorporado que resuelva el desafío.
- Este es el código de golf .
Editar: Eliminar 1
como una entrada potencial.
code-golf
sequence
arithmetic
Paraguas
fuente
fuente
[[1]]
yo diría que si[1,1]
es un gozinta de1
entonces[1,1,12]
es un gozinta de lo12
que es[1,1,1,12]
y ahora podemos ya no "devolver todo ..."2|4
se lee "dos entra en cuatro", también conocido como "dos gozinta cuatro".Respuestas:
Python 3 ,
6865 bytesEditar: -3 bytes gracias a @notjagan
Pruébalo en línea!
Explicación
Cada cadena de gozinta consiste en el número
x
al final de la cadena, con al menos un divisor a la izquierda de la misma. Para cada divisork
dex
las cadenas[1,...,k,x]
son distintas. Podemos por lo tanto para cada divisork
encontrar todos sus distintas cadenas gozinta y anexarx
al final de las mismas, para obtener todas las distintas cadenas gozinta conk
directamente a la izquierda dex
. Esto se hace de forma recursiva hastax = 1
donde[[1]]
se devuelve, ya que todas las cadenas de gozinta comienzan con 1, lo que significa que la recursión ha tocado fondo.El código se vuelve tan corto debido a la comprensión de la lista de Python que permite la doble iteración. Esto significa que los valores encontrados en
f(k)
se pueden agregar a la misma lista para todos los divisores diferentesk
.fuente
Casco , 13 bytes
Un enfoque algo diferente al de H.PWiz , aunque todavía por fuerza bruta. Pruébalo en línea!
Explicación
La idea básica es concatenar todas las subsecuencias
[1,...,n]
y dividir el resultado en sublistas donde cada elemento divide al siguiente. De estos, mantenemos aquellos que comienzan1
, terminann
y no contienen duplicados. Esto se hace con el "rangify" incorporado…
. Luego queda descartar duplicados.fuente
Jalea ,
98 bytesPruébalo en línea!
Utiliza una técnica similar a mi respuesta de Japt y, por lo tanto, se ejecuta muy rápidamente en casos de prueba más grandes.
Cómo funciona
fuente
Mathematica, 77 bytes
Forma a
Graph
donde los vértices son losDivisors
de la entrada#
, y los bordes representan la divisibilidad adecuada, luego encuentraAll
caminos desde el vértice1
hasta el vértice#
.fuente
Jalea , 12 bytes
Un enlace monádico que acepta un entero y devuelve una lista de listas de enteros.
Pruébalo en línea!
¿Cómo?
Queremos todas las listas ordenadas de enteros únicos entre uno y N, de modo que el primero sea uno, el último sea N y todos los pares se dividan. El código logra este filtro al verificar que los criterios de división por pares se satisfacen sobre el conjunto de potencia del rango en cuestión, pero solo selecciona aquellos con sumas máximas de diferencia incremental (los que comienzan con uno y terminan con N tendrán una suma de diferencias incrementales de N-1, otros tendrán menos).
fuente
<slice>2<divisible>\<each>
: PƝ
lugar de '2' para 11 bytes .Japt , 17 bytes
¡Pruébelo en línea!
Extrañamente, generar la salida como una cadena fue mucho más fácil que generarlo como una matriz de matrices ...
Explicación
fuente
¬
truco! : p¬
es una de las razones por las que he implementado un montón de funciones que son básicamente "hacer X sin argumentos, o Y dado un argumento verdadero": PMathematica, 60 bytes
Utiliza la forma multi-arg indocumentado de
Divisible
dondeDivisible[n1,n2,...]
vuelveTrue
sin2∣n1
,n3∣n2
y así sucesivamente, yFalse
de lo contrario. Tomamos todaSubsets
la lista deDivisors
la entrada#
, luego devolvemosCases
la forma{1,___,#}
tal queDivisible
daTrue
laReverse
secuencia d de divisores.fuente
Divisible
es básicamente una construcción para verificar una cadena de gozinta?Haskell, 51 bytes
Recurrentemente encuentre cadenas de gozinta de divisores apropiados y anexe
n
.Pruébalo en línea!
fuente
1
. Como concluimos colectivamente que estamos exentos1
, ¿podría ahorrar 10 bytes eliminando ese caso?1
no es un caso especial para este algoritmo, se necesita como caso base para la recursividad. Por sí sola, la segunda ecuación de definición solo puede devolver la lista vacía.[[1]]
como base.Haskell (Lambdabot),
9285 bytesNecesita Lambdabot Haskell ya que
guard
requiereControl.Monad
ser importado. La función principal es una función anónima, que me han dicho que está permitida y elimina un par de bytes.Gracias a Laikoni por guardar siete bytes.
Explicación:
Las mónadas son muy útiles.
Esta es nuestra función recursiva que hace todo el trabajo real.
x
es el número sobre el que estamos acumulando (el producto de los divisores que permanecen en el valor), yy
es el siguiente número en el que deberíamos intentar dividirlo.Si
x
es igual,y
entonces hemos terminado de recurrir. Solox
úselo como el final de la cadena actual de gozinta y devuélvalo.Haskell golf-ism para "Verdadero". Es decir, este es el caso predeterminado.
Estamos operando dentro de la lista mónada ahora. Dentro de la lista de mónadas, tenemos la capacidad de tomar múltiples decisiones al mismo tiempo. Esto es muy útil cuando se encuentra "todo lo posible" de algo por agotamiento. La
guard
declaración dice "solo considere la siguiente opción si una condición es verdadera". En este caso, solo considere la siguiente opción si sey
dividex
.Si se
y
dividex
, tenemos la opción de agregary
a la cadena de gozinta. En este caso, llame recursivamente(#)
, comenzando de nuevoy = 2
conx
igual ax / y
, ya que queremos "factorizar" lo quey
acabamos de agregar a la cadena. Luego, cualquiera que sea el resultado de esta llamada recursiva, multiplique sus valores por losy
que acabamos de factorizar yy
agreguemos oficialmente a la cadena de gozinta.Considere la siguiente opción también. Esto simplemente agrega las dos listas juntas, pero monádicamente podemos pensar que dice "elegir entre hacer esto o lo otro".
La otra opción es simplemente continuar recurriendo y no usar el valor
y
. Siy
no se dividex
, esta es la única opción. Si sey
divide,x
entonces se tomará esta opción, así como la otra opción, y los resultados se combinarán.Esta es la función principal de gozinta. Comienza la recursión llamando
(#)
con su argumento. A1
se antepone a cada cadena de gozinta, porque la(#)
función nunca los pone en las cadenas.fuente
mod x y==0
se puede acortar amod x y<1
. Debido a que las funciones anónimas están permitidas, su función principal se puede escribir de forma gratuita comomap(1:).(#2)
.Haskell,
10710095 bytesTal vez hay una mejor condición de terminación (probé algo como
pero es más largo) La comprobación de
1
parece prudente ya que la limpieza de repeticiones1
o duplicados (nub
no enPrelude
) es más bytes.Pruébalo en línea.
fuente
(>>=h)
para(concatMap h)
u
...JavaScript (Firefox 30-57), 73 bytes
Convenientemente
n%0<1
es falso.fuente
Jalea , 17 bytes
Pruébalo en línea!
fuente
1
embargo, su resultado es inesperado. No he logrado encontrar un resultado definitivo para1
, pero supuse que era[[1]]
. No puedo decir con certeza que[1,1]
sea incorrecto, excepto que todos los demás resultados son secuencias crecientes. Pensamientos?;€
con;Q¥€
).Mathematica, 104 bytes
fuente
FreeQ[...]
puede convertirseAnd@@BlockMap[#∣#2&@@#&,#,2,1]
Developer
PartitionMap :: nlen: - Texto del mensaje no encontrado - >> `¿por qué es eso?BlockMap
usa laDeveloper`PartitionMap
función internamente, pero como es una función de desarrollador, no tiene mensajes de error. El error es causado por las listas que tienen 1 o 0 elementos, con los que no puede hacer 2 particiones.Mathematica, 72 bytes
Explicación
Encuentra todos los divisores de la entrada.
Genere todos los subconjuntos de esa lista.
Elija todos los casos que coincidan con el patrón ...
Comenzando con 1 y terminando con
<input>
...y satisface la condición ...
El elemento izquierdo divide el elemento derecho para todas las 2 particiones de la lista, desplazamiento 1.
fuente
TI-BASIC, 76 bytes
Explicación
Podría guardar otros 5 bytes si se permite salir con un error en lugar de con gracia, eliminando la verificación Ans> 1 y la condición del bucle. Pero no estoy seguro de que eso esté permitido.
fuente
Mathematica
8677 BytesFuerza bruta por la definición.
Deseando que hubiera una forma más corta de hacer una comparación de elementos secuenciales por pares de una lista.
Gracias a @Jenny_mathy y @JungHwanMin por las sugerencias para guardar 9 bytes
fuente
FreeQ[#∣#2&@@@Partition[#,2,1],1>2]&]
(como segundo argumento) para ir a 82 bytesAnd@@BlockMap[#∣#2&@@#&,#,2,1]
Casco ,
1716 bytes-1 byte, gracias a Zgarb
Pruébalo en línea!
fuente
50
la entrada y expiró. ¿Cuál es la esencia de su enfoque?o`:⁰:1
puede ser`Je1⁰
PHP
147141Editado para eliminar una prueba redundante
Explicado:
15 caracteres de repetitivo :(
Inicie el conjunto de resultados a
[[1]]
medida que cada cadena comience con 1. Esto también lleva a admitir 1 como entrada.Para cada número del 2 al
$i
, vamos a extender cada cadena en nuestro conjunto por el número actual si va a ser , luego, agrega la cadena extendida a nuestro conjunto de resultados.Filtra nuestras cadenas intermedias que no llegaron a
$i
10 caracteres de repetitivo :(
fuente
Mathematica
La respuesta se almacena en caché para llamadas adicionales.
fuente