Haz los números más grandes y más pequeños


13

Inspirado en esta publicación sobre Puzzling. Spoilers de ese rompecabezas están a continuación.

Dados tres enteros positivos como entrada, (x, y, z)construya el rango inclusivo [x, y], concatene ese rango juntos, luego elimine zdígitos no necesariamente consecutivos para producir los enteros positivos más grandes y más pequeños posibles. Los ceros iniciales no están permitidos (es decir, los números deben comenzar con [1-9]). Emite esos dos números en cualquier orden.

Para el ejemplo de la publicación Puzzling, para la entrada (1, 100, 100), el número más grande posible es 99999785960616263646566676869707172737475767778798081828384858687888990919293949596979899100,
y el número más pequeño es 10000012340616263646566676869707172737475767778798081828384858687888990919293949596979899100,
siguiendo la lógica a continuación de la respuesta de jafe publicada allí:

  • No podemos influir en la longitud del número (hay un número fijo de dígitos), por lo que para maximizar el valor tomamos el primer dígito máximo, luego el segundo dígito, etc.
  • Elimine los 84 primeros no nueves (quedan 16 dígitos para eliminar): 999995051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  • El número más grande dentro de los siguientes 17 dígitos es 7, por lo que a partir de aquí, el siguiente dígito en la respuesta puede ser como máximo 7 (no podemos eliminar más de 16 dígitos). Entonces, elimine 15 no 7 ... (queda 1 dígito para eliminar):999997585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  • A partir de aquí, el siguiente dígito puede ser como máximo 8, así que elimine uno que no sea 8 del medio: 99999785960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  • Lógica similar, pero invertida (es decir, queremos una 1s principal en lugar de una 9s inicial ) para el número más pequeño.

Aquí está un ejemplo más pequeña: (1, 10, 5).

Construimos el rango 12345678910y determinamos qué 5dígitos podemos eliminar dejando el mayor número posible. Obviamente, eso significa que queremos maximizar el dígito inicial, ya que no podemos influir en la longitud de la salida. Entonces, si eliminamos 12345, nos quedamos 678910, y eso es lo más grande que podemos hacer. Hacer el más pequeño es un poco más complicado, ya que podemos extraer los números del medio en su lugar, dejando 123410el más pequeño posible.

Para (20, 25, 11), el resultado es bastante aburrido, como 5y 1.

Finalmente, descartar respuestas que intentan poner ceros a la izquierda, (9, 11, 3)da lo 91011que a su vez rinde 91y 10es el más grande y el más pequeño.

E / S y reglas

  • Si es más fácil / más corto, puede codificar dos programas / funciones, uno para el más grande y otro para el más pequeño, en cuyo caso su puntaje es la suma de ambas partes.
  • La entrada y salida se pueden dar por cualquier método conveniente .
  • Se puede suponer que la entrada encaja en el tipo de número nativo de su idioma, sin embargo , no se puede suponer que el número concatenado ni la salida lo hagan.
  • Un programa completo o una función son aceptables. Si es una función, puede devolver el resultado en lugar de imprimirlo.
  • Las lagunas estándar están prohibidas.
  • Este es el por lo que se aplican todas las reglas habituales de golf, y gana el código más corto (en bytes).

¿Una lista de dígitos es aceptable como salida?
Rod

Un caso de prueba que arrojaría un mínimo falso al evaluar a aquellos con ceros a la izquierda puede valer la pena, creo que 9, 11, 3lo haría.
Jonathan Allan

@ Rod Sí, una lista de dígitos está bien para la salida.
AdmBorkBork

@ Rod No sé de qué estás hablando, claramente escribí "salida" arriba. ;-)
AdmBorkBork

@ JonathanAllan Buena llamada. Adicional.
AdmBorkBork

Respuestas:


5

Haskell , 162 bytes

l=length
((m,f)%n)s|n>=l s=[]|n>0,(p,c:r)<-span(/=m(f$take(n+1)s))s=c:((m,id)%(n-l p)$r)|1>0=s
(x#y)z=[p%z$show=<<[x..y]|p<-[(maximum,id),(minimum,filter(>'0'))]]

Pruébalo en línea!

Utiliza el algoritmo descrito por jafe. Puede ser más corto usar un método menos eficiente, pero fue más divertido escribirlo :)

La %operación toma 4 argumentos (en realidad 3, pero lo mque sea): que es una función que selecciona el miembro "óptimo" de una lista (ya sea maximumo minimumsegún lo que queramos); fque es una función de "filtro"; nel número de dígitos que quedan para soltar; y sla cuerda Primero verificamos si n es igual al número de dígitos que quedan en la cadena (lo usé >=por seguridad) y descartamos el resto de ssi es así. De lo contrario, verificamos si aún necesitamos soltar dígitos ( n>0), luego usamos spanpara dividir nuestra cadena en tres partes: plos dígitos para soltar, cel dígito óptimo alcanzable yrla cuerda restante Hacemos esto al pasar un predicado que verifica la igualdad contra nuestro dígito óptimo. Para encontrar ese dígito tomamos los primeros n+1dígitos de la cadena, lo filtramos y luego lo pasamos a nuestra función "selector". Ahora solo producimos nuestro dígito óptimo y repetimos, restando la longitud de p(la cantidad de dígitos eliminados) de n. Tenga en cuenta que no pasamos nuestra función de filtrado a la llamada recursiva y, en su lugar, la reemplazamos con id. Esto se debe a que el filtro solo está ahí para evitar seleccionar ceros iniciales en el minimumcaso, que solo es relevante en la primera iteración. Después de eso ya no necesitamos ningún filtro.

%es en realidad sólo una función de ayuda para los #que es nuestra función "real", tomando x, yy z. Utilizamos una lista de comprensión solo para evitar un poco de repetición, iterando sobre nuestras tuplas de funciones y pasándolas %junto con zy la cadena concatenada. Esa cadena se crea utilizando el operador de mónada mágica (=<<)que, en este contexto, funciona como concatMap.


3

Jalea , 17 bytes

r/VDœcL_¥¥ḷ/ƇVṢ.ị

Pruébalo en línea!

Calcula todas las posibilidades y luego mantiene la más grande y la más pequeña.

Argumento a la izquierda: x,ypara construir el rango. Argumento correcto: zdígitos a eliminar.

r/VDœcL_¥¥ḷ/ƇVṢ.ị
r/                 Inclusive range from x to y
  V                Concatenate the digits together
   D               Get the resulting digits
         ¥         Dyad:
        ¥            Dyad:
      L                Length of the list of digits in the concatenated number.
       _               Subtract the number of digits to be removed.
    œc               Combinations without replacement. (remove z digits)
            Ƈ      Keep lists of digits that:
          ḷ/       have a positive first element (no leading zeros).
             V     Combine digits into integers. (vectorizes to ldepth 1)
              Ṣ    Sort the numbers
               .ị  Indexes at value 0.5 which yields the first and last elements.

2

Python 2 , 143 bytes

import itertools
s,e,r=input()
l=''.join(map(str,range(s,e+1)))
L=[i for i in itertools.combinations(l,len(l)-r)if'0'<i[0]]
print min(L),max(L)

Pruébalo en línea!

Esto funciona calculando todas las combinaciones del tamaño objetivo (se preserva el orden del elemento) y obteniendo los números más pequeños / más grandes


Oh ... supongo que eso funciona jajaja. Estaba intentando realmente hacer un programa que realmente lo calcule de manera determinista.
Don Miles

@RushabhMehta Los cálculos de fuerza bruta siguen siendo deterministas, solo que más lentos.
dylnan

2

Carbón , 56 bytes o 21 + 46 35 = 67 56 bytes

≔⪫…·NNωθFN≔⌈EθΦθ⁻λνθθ

Pruébalo en línea! El enlace es a la versión detallada del código. Explicación:

≔⪫…·NNωθ

Ingrese xy y, cree un rango inclusivo y una los números en una cadena.

FN

Haga un bucle por cada dígito que se eliminará.

≔⌈EθΦθ⁻λνθ

Cree una lista de cadenas formadas eliminando cada posible carácter de la cadena actual y tome el máximo.

θ

Imprime el resultado.

≔⪫…·NNωθF⊕N⊞υωΦθ∧⁼ι⌊Φ✂θκLυ¹∨κIλ⊞Oυω

Pruébalo en línea! El enlace es a la versión detallada del código. Explicación:

≔⪫…·NNωθ

Ingrese xy y, cree un rango inclusivo y una los números en una cadena.

F⊕N⊞υω

Ingrese ze increméntelo. Luego creo una lista de esa longitud: necesito poder incrementar zdentro del siguiente filtro, pero solo los comandos pueden incrementar variables; hay una laguna en esoPushOperator aumenta la longitud de la lista.

 θ                      String of digits
Φ                       Filter over characters
         κ              Current index
          Lυ            Length of list i.e. current `z` value
            ¹           Literal 1
       ✂θ               Slice string of digits
      Φ                 Filter over characters
              κ         Outer index
               Iλ       Cast inner character to number
             ∨          Logical OR
     ⌊                  Minimum
   ⁼ι                   Equals the outer character
  ∧              ⊞Oυω   And also push to list i.e. increment `z`
                        Implicitly print

Filtre los caracteres que desee comprobando que no haya caracteres más bajos en la región divisible. La región comienza con el primerz+1 caracteres (ya que es posible cortar el primero zsi es necesario) y el punto final se incrementa para cada carácter que se mantiene. Se tiene cuidado de no elegir un cero para el primer personaje.

El algoritmo más rápido es de 30 bytes cuando se usa para calcular el mayor número posible:

≔⪫…·NNωθF⊕N⊞υωΦθ∧⁼ι⌈✂θκLυ¹⊞Oυω

Pruébalo en línea! El enlace es a la versión detallada del código. Editar: desde entonces pude combinar los dos anteriores en una segunda solución de 56 bytes que genera ambos resultados:

≔⪫…·NNωθF⊕N⊞υω≔⮌υη⟦Φθ∧⁼ι⌈✂θκLυ¹⊞OυωΦθ∧⁼ι⌊Φ✂θκLη¹∨κIλ⊞Oηω

Pruébalo en línea! El enlace es a la versión detallada del código. Explicación:

≔⪫…·NNωθ

Genera la cadena inicial.

F⊕N⊞υω

Representar z+1como la longitud de la lista.

≔⮌υη

Invierta la lista clonándola y guarde el resultado.

Imprima los dos resultados en líneas separadas. (Otra forma de hacerlo es separar los resultados con un \rcarácter literal ).

Φθ∧⁼ι⌈✂θκLυ¹⊞Oυω

Genera el mayor número posible.

Φθ∧⁼ι⌊Φ✂θκLη¹∨κIλ⊞Oηω

Genere el número más pequeño posible utilizando la lista clonada para realizar un seguimiento z.


1

Jalea ,  19  18 bytes

rDẎœcL_⁵Ɗ$ị@Ƈ1ḌṢ.ị

Pruébalo en línea!

Muy ineficiente, definitivamente no tiene sentido ir 1, 100, 100como(19292)=305812874887035355118559193163641366325011573739619723360


1

05AB1E , 16 bytes

ŸSDg³-.Æʒ¬Ā}{Ć`‚

Pruébalo en línea!

Programa completo, leyendo entradas en este orden: y, x, z . Emite una lista de dos listas de caracteres.

Explicación

ŸSDg³-.Æʒ¬Ā}{Ć`‚    Full program. Inputs: y, x, z.
Ÿ                   Inclusive binary range from x to y. Push [x ... y].
 S                  Dump the digits separately in a list.
  Dg                Duplicate, and use the second copy to get its length.
    ³-              Subtract z from the length.
      .Æ            Retrieve all combinations of length - z elements from the digits.
        ʒ  }        Keep only those that...
         ¬Ā         Don't start with a 0 (head, then Python-style boolean).
            {       Sort the remaining elements.
             Ć      Enclose. Pushes list + list[0] (appends its tail to itself)
              `     Dump all elements separately on the stack.
               ,    Pair, to get the last two, min and max (after enclosing)

Oh, Ć`‚es bastante inteligente, buena respuesta!
Kevin Cruijssen

0

Matlab, 95 bytes

function[m]=f(s,e,c),a=sprintf('%d',s:e);x=str2num(combnk(a,length(a)-c));m=[min(x),max(x)];end

Pruébalo en línea!

Devuelve una matriz 1x2 con min y max.

Cómo funciona

% Full code
function[m]=f(s,e,c),a=sprintf('%d',s:e);x=str2num(combnk(a,length(a)-c));m=[min(x),max(x)];end

% The function
function[m]=f(s,e,c),                                                                       end

                     % Creates the range in a single string
                     a=sprintf('%d',s:e);

                                                   % Gets all the combinations
                                                   combnk(a,length(a)-c)

                                         % Converts the string combinations to integers
                                         x=str2num(                     );

                                                                          % Finds min and max
                                                                          m=[min(x),max(x)];
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.