Rosencrantz y Guildenstern son Code

10

En la obra absurda Rosencrantz y Guildenstern están muertos , los dos personajes principales Rosencrantz y Guildenstern (¿o son ellos?) Siempre están mezclando cuál de ellos es quién o, a veces, cuál de sus propias partes del cuerpo es cuál, debido a la falta percibida de identidad individual ¿No sería absurdo si incluso barajaran sus nombres?

Su tarea es escribir una función que tome una cadena de una longitud par (y por diseño, un múltiplo de 4) que tenga más de 7 caracteres, dividirla y barajarla.

La división será la siguiente : la cadena tendrá formato "abscd", y s actuará como un carácter separador. La primera sección y el separador absserán la primera mitad de la cadena, mientras que la segunda mitad serácd

La longitud de aserá(string length / 4) - 1

La longitud de bserá(string length / 4)

La longitud de sserá1

La longitud de cserá(string length / 4) + 1

La longitud de dserá(string length / 4) - 1

Esto puede ser realmente confuso, así que déjame mostrarte algunos ejemplos

("a" + "bb" + "s" + "ccc" + "d").length //8
  1     2      1      3      1
|-------4--------|  |----4-----| <--- (4 is half of 8)

("rosen" + "crantz" + "&" + "guilden" + "stern").length  //24
    5         6        1        7          5

("foo" + "barr" + "?" + "barry" + "foo").length
   3       4       1      5         3

Finalmente:

Luego barajas las partes, generando adscb

ex. "rosencrantz&guildenstern" --> "rosenstern&guildencrantz"

"foobarr?barryfoo" --> "foofoo?barrybarr"

Rulez:

  1. Las lagunas estándar están prohibidas
  2. Respuestas aceptables: una función que toma la entrada a través de una cadena de entrada y devuelve una cadena de salida
  3. Si la cadena de entrada no coincide con los requisitos proporcionados anteriormente, su código DEBE dar error (no importa qué tipo de Exceptiono Error)
  4. Esto es code-golf, ¡entonces la respuesta más corta (válida) (en cada idioma) gana!
  5. Puntos de bonificación para una línea :-) (No realmente, solo puntos geniales)
Miguel
fuente
66
Con respecto a su norma gangsta: generalmente se desaconseja favorecer las "funciones" , ya que son difíciles de definir en general. Además, el manejo de entradas no válidas también se evita principalmente, ya que generalmente se reduce a un código molesto de placa de caldera.
Jonathan Frech
@JonathanFrech Creo que el desafío de la validación de entrada es un problema interesante, ya que se puede manejar de varias maneras, desde el recorrido de la matriz, hasta la lógica de ramificación y las pruebas RegEx, por lo que la optimización de estos puede agregar un desafío adicional ¯_ (ツ) _ / ¯ Intentaré eso para otro desafío de código de golf :-)
Michael
2
tfw todos están tratando de obtener métodos io más flexibles para hacer el código en su idioma de golf favorito. y tfw sucede en casi todas las preguntas
Windmill Cookies
1
@NathanMerrill Se menciona en la especificación que la entrada debe tener más de 7 caracteres de longitud y su longitud debe ser divisible por cuatro, Jo King estaba sugiriendo una entrada de caso de prueba de longitud 4 como "abcd" que debería
fallar

Respuestas:

11

K (oK) , 35 34 33 bytes

{$[8>#x;.;<x!4!-&4#-1 0 2+-4!#x]}

Pruébalo en línea!

Sin validación de entrada (para la recompensa de ngn), 25 24 23 bytes

{<x!4!-&4#-1 0 2+-4!#x}

Pruébalo en línea!

Aprendí rápidamente un poco de K y, al mirar la lista de verbos, pensé que un enfoque alternativo ( no usar cortar) podría funcionar aquí. Y funcionó perfectamente.

Cómo funciona

{<x!4!-&4#-1 0 2+-4!#x}
                 -4!#x    Length divided by four (floor division)
        4#-1 0 2+         Generate lengths (x/4-1, x/4, x/4+2, x/4-1)
       &                  Generate that many 0, 1, 2, 3's
    4!-                   Negate and modulo 4; effectively swap 1 and 3
 <x!                      Sort the original string by above

{$[8>#x;.; <code> ]}  Input validation
 $[8>#x           ]   If the length is less than 8
        .             Dynamically generate an error
           <code>     Otherwise, run the main code
Bubbler
fuente
@ngn Lo que le pasó a mis ojos Oo
Bubbler
3

Perl 6 , 60 58 bytes

-2 bytes gracias a Jo King

{[~] .rotor($_/4 X-1,0,+^-$_+>2,-1,1)[0,4,2,3,1;*]}o*.comb

Pruébalo en línea!

Lanza "La longitud de la sublista de rotación está fuera de rango" en caso de error.

Explicación

{               # Anonymous block
 [~]            # Join
   .rotor(      # Split into sublists of specific length
     $_/4 X-    # Subtract from len/4
     1,
     0,
     +^-$_+>2,  # (len-1)>>2
                #   subtraction yields 1 if len is multiple of 4
                #   otherwise a value less than 1 causing an error
     -1,       
     1)
   [0,4,2,3,1;*]  # Rearrange sublists and take inner elements
}o*.comb          # Split into characters and feed into block
nwellnhof
fuente
3

J , 36 35 bytes

5;@A.](<;.2~;)1<@{."+~1 0 _2 1-4%~#

Pruébalo en línea!

-1 byte por {.+ longitudes negativas y ;.2que corta en unos como marcadores "finales" en su lugar.

Respuesta original, 36 bytes

5;@A.](<;.1~;)1<@{."+~_1 0 2 _1+4%~#

Pruébalo en línea!

ngn mencionó "cortar" en un comentario a una respuesta anterior de K , y me hizo probar J, que tiene el mismo "corte" (no tengo idea de cómo funciona K).

Cómo funciona

5;@A.](<;.1~;)1<@{."+~_1 0 2 _1+4%~#  Monadic train.
                                4%~#  Length divided by four
                      _1 0 2 _1+      Generate the four segment lengths
              1<@{."+~  Generate [1 0 0...] boxed arrays of those lengths
      (     ;)          Raze; unbox and concatenate
     ] <;.1~            Cut the input string on ones as starting marker, then box each
5  A.  Rearrange the boxes in the order 0 3 2 1
 ;@    Raze again

Tenga en cuenta que esta función maneja automáticamente las entradas no válidas:

  • Si la longitud de entrada no es múltiplo de cuatro, {.arroja domain errorya que su argumento de longitud tiene que ser enteros.
  • Si la longitud de entrada es 4, el corte produce solo dos segmentos y se 5 A.lanza index error.
  • Si la longitud de entrada es 0, los dos argumentos para cortar no tienen la misma longitud, por lo que length errorse arroja.
Bubbler
fuente
3

Python 3 , 103 102 101 97 88 86 84 bytes

def f(s):l=len(s);l//=4*(l%4<1<l/4);return s[:l-1]+s[1-l:]+s[2*l-1:1-l]+s[l-1:2*l-1]

Pruébalo en línea!

Realmente no es una línea, pero ;es un byte menos por línea que el salto de línea y la sangría.

Lanza ZeroDivisionErrorsi la longitud de la cadena de entrada es menor que 8 o no es un múltiplo entero de 4.

También funciona en Python 2.

-4 bytes gracias a Jo King

-9 bytes gracias a los ovs

-2 bytes gracias a Jonathan Frech

-2 bytes gracias a Bubbler

Axim
fuente
@JoKing gracias por los consejos, muy apreciados :)
Axim
1
88 bytes
ovs
@ovs buena captura en los índices adyacentes, en cuanto a los parens, probé durante al menos 20 minutos para ver si podía deshacerme de algunos de ellos, luego me perdí por completo con el cambio al //=par más externo que se volvió redundante. ¡Gracias un montón!
Axim
2
-l+1<-> 1-l?
Jonathan Frech el
1
Combina las dos desigualdades para llegar a 84 bytes .
Bubbler el
2

Perl 6 , 78 bytes

*.comb[0..*/4-2,3* */4+1..*,*/2-1/(*>7)..3* */4,*/4-1/(*%%4)..*/2-2].flat.join

Pruébalo en línea!

Bloque de código anónimo que toma una cadena y devuelve la cadena modificada si es válida; de lo contrario, devuelve un error de división por cero. Sé que puedo modificar una matriz directamente, por lo que podría intercambiar las dos secciones de la cadena, pero no puedo entenderlo.

Jo King
fuente
2

K (NGN / K) , 120 113 103 99 95 bytes

{$[(r>7)&0=4!r:#:x;{g:(s:*|(y*2)#x)\x;((y-1)#*g),((-y-1)#*|g),s,((y+1)#*|g),(-y)#*g}[x;r%4];l]}

Es de esperar que se pueda jugar más, incluyó una función adicional para probar si la longitud de la cadena es divisible por cuatro, genera un error con referencia a la variable no declarada si la entrada no es válida

EDITAR: Condición perdida en longitud mayor que 7, incluida

EDITAR: combinado en una función, elimina las declaraciones de variables redundantes

Pruébalo en línea!

Thaufeki
fuente
1
Esto podría ser mucho más corto. sabes acerca de "cortar" ( indices_string)? hazme un ping en el huerto si debo explicarlo
NGN
1
puedo hacerlo en 34 bytes :)
ngn
Sé acerca de cortar, pero no pensé en usarlo ... ¿34 bytes? Voy a tener que darle otra oportunidad cuando llegue a casa y ver si me
acerco a
Debo mencionar: mi solución no se asegura de que las entradas no válidas (longitud <= 7) causen un error
ngn
1

Retina 0.8.2 , 58 o 73 o 83 o 93 bytes

((((.)))*?)(.(?<-2>.)+)(...(?<-3>.)+)((?<-4>.)+)$
$1$7$6$5

Pruébalo en línea! Explicación:

((((.)))*?)

Capturar aen$1 , y que sea lo más corto posible *?. $#2, $#3y $#4terminan como la longitud de a.

(.(?<-2>.)+)

Capturar b adentro $4. Las (?<-2>.)+capturas hasta la longitud de a, mientras que el otro .agrega 1 a su longitud según sea necesario.

(...(?<-3>.)+)

Capturar s y cen $6. Su longitud combinada es tres más que la longitud de a.

((?<-4>.)+)

Captura dadentro $7. Su longitud no es más que la longitud de a.

$

Hicimos lo amás corto posible, pero aún queremos llegar al final de la entrada.

$1$7$6$5

Intercambio by d.

La etapa anterior no valida su entrada. Como Retina no tiene errores de tiempo de ejecución, hay varias opciones para la validación de entrada:

G`^(....){2,}$

No genera nada si la longitud es inferior a 8 o no es múltiplo de 4. (+15 bytes)

^(?!(....){2,}$).*
Error

Salidas Error si la longitud es menor que 8 o no es múltiplo de 4. (+25 bytes)

+`^(....)*..?.?$|^(....)?$
.....$1

Se bloquea si la longitud es inferior a 8 o no es múltiplo de 4. (+35 bytes)

Neil
fuente
Esto no arroja un error en las entradas no válidas (por muy molesto que sea)
Jo King
1

C (gcc) con -Dx=memcpyy -DL=(l-1), 154 158 160 bytes

Devuelve NULL si la longitud de la cadena de entrada no es divisible por 4 o más corta que 8 caracteres.

Gracias a Rogem y Jonathan Frech por las sugerencias.

EDITAR: El preprocesador movido define la línea de comando e hizo que la cadena se asigne dinámicamente para ajustarse estrictamente al rompecabezas.

f(s,t,l)char*s,*t;{l=strlen(s);l%4|l<8?t=0:(t=malloc(l+1),l/=4,x(t,s,L),x(t+L,s+3*l+1,L),x(t+2*L,s+L+l,l+2),x(t+3*l,s+L,l),t[4*l]=0);l=t;}//-Dx=memcpy -DL=(l-1)

Pruébalo en línea!

ErikF
fuente
¿Por qué t[80]? No parece haber un límite superior con respecto a la longitud de entrada.
Jonathan Frech el
@ JonathanFrech Lo hice para guardar bytes pero estás en lo correcto. He cambiado la solución para usar malloc()en su lugar.
ErikF
Devuelve por modificación, el valor de retorno es NULLpara resultados no válidos, utiliza valores de retorno de memcpy(), una macro similar a una función para omitir los tipos y matrices de longitud variable C99 para omitir malloc().
¿Por qué 160 bytes, cuenta el //o el -w?
l4m2
@ l4m2 -wes solo una conveniencia para suprimir advertencias (por lo que los errores son más fáciles de encontrar). Por lo general, agrego argumentos de línea de comando después //de que TIO cuente sus bytes por mí, y luego deduzco 1 del total para tener en cuenta el carácter adicional necesario para hacer eso.
1

Jalea , 28 bytes

L7»4ḍİ×L:4;;ĖÄƲFÄœṖ⁸⁽%[D¤ị$F

(Si se permite un programa completo, podemos eliminar el final F)
Si la longitud es menor que 8 o no es divisible por cuatro a ValueErrorse eleva durante la división entera de inf(un flotante) por 4- la división produce NaN(también un flotante) que luego no puede ser lanzado a un int.

Pruébalo en línea!

¿Cómo?

L7»4ḍİ×L:4;;ĖÄƲFÄœṖ⁸⁽%[D¤ị$F - Link: list of characters
L                            - length
 7                           - literal seven
  »                          - maximum (of length & 7)
   4ḍ                        - divisible by four? (yields 1 for good inputs; 0 otherwise)
     İ                       - inverse (1 yields 1; 0 yields inf)
      ×L                     - multiply by length (length or inf)
        :4                   - integer divide by 4 (errors given inf)
              Ʋ              - last four links as a monad (f(x)):
          ;                  -   concatenate -> [x,x]
            Ė                -   enumerate -> [1,x]
           ;                 -   concatenate -> [x,x,[1,x]]
             Ä               -   cumulative sum (vectorises at depth 1) -> [x,x,[1,1+x]]
               F             - flatten -> [x,x,1,1+x]
                Ä            - cumulative sum -> [x,2x,2x+1,3x+2]
                   ⁸         - chain's left argument (the input)
                 œṖ          - partition at indices (chops up as per requirements)
                          $  - last two links as a monad (f(z)):
                        ¤    -   nilad followed by link(s) as a nilad:
                    ⁽%[      -     10342
                       D     -     decimal digits -> [1,0,3,4,2]
                         ị   -   index into z (rearranges the pieces as per requirements)
                           F - flatten (back to a list of characters)
Jonathan Allan
fuente
1

Jalea , 25 bytes

L:4’+“¡¢¢£¡‘Ṡ3¦ÄṬk⁸Ṛ2,5¦Ẏ

Pruébalo en línea!

Se puede eliminar para convertir esto en un programa completo.

Erik el Outgolfer
fuente
1

JavaScript (ES6), 97 89 bytes

Guardado 8 bytes gracias a @ l4m2

s=>(l=s.length/4)<2||l%1?Z:s.replace(eval(`/(.{${l}})(.{${l+2}})(.{${l-1}})$/`),'$3$2$1')

Pruébalo en línea!

Arnauld
fuente
1
89B
l4m2
0

Java 8, 135 bytes

s->{int l=s.length();l=l>7&l%4<1?l/4:l/0;return s.substring(0,l-1)+s.substring(3*l+1)+s.substring(2*l-1,3*l+1)+s.substring(l-1,2*l-1);}

Lanza ArithmeticException(se divide por cero) si la cadena de entrada no coincide con los requisitos. Pruébelo en línea aquí .

Sin golf:

s -> { // lambda function taking a String argument and returning a String
    int l = s.length(); // take the length of the input ...
    l = l > 7 &         // ... if it's  greater than 7 and ...
        l % 4 < 1       // ... a multiple of 4 ...
      ? l / 4           // ... divide by 4; otherwise ...
      : l / 0;          // ... error out (division by zero throws ArithmeticException)
    return // concatenate and return:
           s.substring(0, l - 1)             // a
         + s.substring(3 * l + 1)            // d
         + s.substring(2 * l - 1, 3 * l + 1) // sc
         + s.substring(l - 1, 2 * l - 1);    // b
}
OOBalance
fuente
Sugerir en l/=l>7&l%4<1?4:0;lugar del=l>7&l%4<1?l/4:l/0;
ceilingcat
0

C (gcc) , 129 bytes

Devoluciones por modificación. Compilar con:

-Df(s)=({char t[l=strlen(s)];l%4|l<8?0:(l/=4,x(t,s+l*2-1,l-~l),x(x(x(s+l*3,s+l-1,l)-l-2,t,l+2)-l+1,t+l+2,l-1),s);}) -Dx=memcpy

Archivo fuente:

l;

Pruébalo en línea!

Degolf

-Df(s)=({ // Function-like macro f. Takes a char* as a parameter.
          // Return value is a pointer to s if successful, and to NULL if string was invalid.
     char t[l=strlen(s)]; // Allocate a local temp string.
     l%4|l<8?0: // Detect invalid strings. Return 0 (NULL) on invalid string.
         (l/=4, // We're only really concerned with floor(len/4), and this will yield that.
             memcpy(t,s+l*2-1,l-~l), // Copy the second half of chars to the temp storage.
             memcpy( // Because memcpy returns the address of the destination, we can chain
                     // the calls to save quite a few bytes, even after x->memcpy substitution.
                 memcpy(memcpy(s+l*3,s+l-1,l) // Next, copy the second quarter to the end.
                     -l-2,t,l+2) // After that, we copy back the third quarter to its place.
                          -l+1,t+l+2,l-1) // Finally, copy the fourth quarter to where the second
                                          // quarter was.
                      ,s);}) // And return the pointer.

fuente