Invertir un algoritmo de cubo de Rubik

19

Cada vez que haces un movimiento en un Cubo de Rubik, hay un movimiento inverso que deshace el primer movimiento. Debido a esto, cada algoritmo (conjunto de movimientos) tiene un algoritmo inverso que deshace el primer algoritmo.

El objetivo de este desafío es encontrar el reverso de un algoritmo dado.

Especificación:

La entrada consiste en una matriz de movimientos individuales. Cada movimiento es una cadena de longitud 1 o 2. Por supuesto, puede usar cualquier formato de entrada que tenga más sentido en su idioma. Cada movimiento consiste en la estructura Xor X'o X2, donde Xhay una letra mayúscula o minúscula.

Para revertir X, simplemente reemplácelo con X'. Del mismo modo, se X'convierte X. X2por otro lado no se cambia.

Para crear la salida, invierta cada movimiento y luego invierta la matriz.

Ejemplos (cadenas separadas por espacios):

R => R'

D U' => U D'

S T A C K => K' C' A' T' S'

A2 B2 => B2 A2

Puntuación:

Este es el código de golf, por lo que gana la menor cantidad de bytes. Las lagunas estándar no están permitidas.

Julian Lachniet
fuente
¿Está permitido R2-> R2'o B-> B3?
CalculatorFeline
2
Tener que manejar X3o X1habría sido una buena adición al desafío.
Shaggy
1
"Debido a esto, cada algoritmo (conjunto de movimientos) tiene un algoritmo inverso que deshace el primer algoritmo" ¿es esto cierto para todos los algoritmos? Porque creo que los algoritmos de hash son unidireccionales. Significa que no tiene ningún algoritmo inverso, ¿verdad? por favor hágamelo saber
Avishek Saha
44
@AvishekSaha: Para los problemas del Cubo de Rubik, "algoritmo" se limita al significado "una secuencia de movimientos que puedes hacer en el Cubo". En este sentido, no existe un algoritmo de hashing unidireccional en el Cubo.
Ross Presser
55
Debería haber tenido D2R2como caso de prueba ...
Neil

Respuestas:

7

Python 2 , 71 57 54 53 bytes

-15 bytes gracias a los ovs! -3 bytes gracias a Rod.

lambda l:[i.strip("'")+" '"[len(i):]for i in l[::-1]]

Pruébalo en línea!

Cadena de E / S, 70 bytes

lambda s:' '.join(i.strip("'")+"'"*(len(i)<2)for i in s.split()[::-1])

Pruébalo en línea!

totalmente humano
fuente
1
53 bytes
ovs
7

V , 13 10 bytes

æGÇä/á'Ó''

Pruébalo en línea!

3 bytes guardados gracias a @nmjmcman señalando mi característica favorita. Explicación:

æG          " Revere the order of every line
  Ç         " On every line not containing...
   ä/       " a digit:
     á'     "   Append an '
       Ó    "   Remove every instance on this line
        ''  "     Of two single quotes
DJMcMayhem
fuente
¿ äLe gusta representar una expresión regular cuando se compila en vim?
Downgoat
@Downgoat ¡Sí! Lo hace. Traducido a vim, esta solución es :g!/\d/norm A'<CR>:%s/''//g<CR>gg:g/^/m0<CR>Más información sobre cómo V comprime las expresiones regulares se puede encontrar aquí
DJMcMayhem
@DJMcMayhem ¿No son finales implícitos como su característica favorita? Pruébalo en línea!
nmjcman101
3
Sé que es bastante tarde, pero esto no funciona para mí. Convierte un R2 en un 2R, lo cual no es válido
Jamie Sanborn
7

Retina 0.8.2 , 27 26 bytes

\w
$&'
''

'2'
2
O$^`.'?2?

Pruébalo en línea! El enlace incluye casos de prueba. Explicación: La primera etapa agrega un apóstrofe después de cada alfanumérico. Esto da como resultado dobles apóstrofes (con o sin un 2 incluido) que deben eliminarse. La etapa final invierte los movimientos.

Neil
fuente
¿Podría mejorarse esto con el lanzamiento de Retina 1.0 ?
MD XF
@MDXF Parece que O$^de hecho sigue siendo la mejor manera de revertir una lista de coincidencias, por lo que el recuento de bytes no ha cambiado en la Retina 1.
Neil
5

JavaScript (ES6), 45 bytes

s=>s.map(([a,b])=>b?+b?a+b:a:a+"'").reverse()

La solución más corta es tomar Array IO. Uso simple y apropiado de la destrucción de argumentos.

La salida de cadena es de +8 bytes para .join` `.

Entrada de cadena, salida de matriz: 69 bytes

(s,k=[])=>s.replace(/\S\S?/g,([a,b])=>k.unshift(b?+b?a+b:a:a+"'"))&&k

f=

(s,k=[])=>s.replace(/\S\S?/g,([a,b])=>k.unshift(b?+b?a+b:a:a+"'"))&&k

;

console.log(["R", "D U'", "S T A C K", "A2 B2"].map(e => `${e} => ${f(e)}`));
<textarea oninput="out.value=(f(this.value)||[]).join` `" placeholder="input here"></textarea>
<textarea id="out" readonly></textarea>

Conor O'Brien
fuente
Buena esa. ¿Por qué nunca pienso en desestructurar los parámetros de la función? :(
Shaggy
Usted debe ser capaz de reemplazar .reverse()con ::reverseahorro de 1 byte, pero haciendo ES7
Downgoat
@Downgoat ¿Algún lugar donde pueda probar ES7?
Conor O'Brien
@ ConorO'Brien puede usar REPL en línea de babel (marque ejecutar y todos los cuadros preestablecidos para todas las funciones): babeljs.io/repl
Downgoat
4

Jalea , 11 bytes

ḟ;ċ?”'ḣ2µ€Ṛ

Un enlace monádico que devuelve una lista de listas de caracteres (una "matriz" de "cadenas").

Pruébalo en línea!(El pie de página evita romper la salida, mostrando la lista dividida con espacios).

¿Cómo?

ḟ;ċ?”'ḣ2µ€Ṛ - Link: list of lists of characters             e.g. ["F'", "D2" , "R"]
        µ€  - perform the chain to the left for €ach turn instruction:
    ”'      -   literal "'" character
   ?        -   if:
  ċ         -     count (number of "'" in the instruction) i.e.:  1   , 0    , 0
ḟ           -   then: filter out                                  "F"
 ;          -   else: concatenate                                       "D2'", "R'"
      ḣ2    -   head to index 2                                   "F" , "D2" , "R'"
          Ṛ - reverse                                            ["R'", "D2" , "F"]
Jonathan Allan
fuente
10 bytes con nueva gelatina.
user202729
4

JavaScript (ES6), 46 bytes

Toma datos como una serie de movimientos.

a=>a.map(m=>m[1]?+m[1]?m:m[0]:m+"'").reverse()

Pruébalo

Ingrese una lista de movimientos separados por comas.

o.innerText=(f=
a=>a.map(m=>m[1]?+m[1]?m:m[0]:m+"'").reverse()
)((i.value="S,T,A,C,K").split`,`);oninput=_=>o.innerText=f(i.value.split`,`)
<input id=i><pre id=o>


Explicación

a=>

Función anónima que toma la matriz de movimientos como argumento a través de un parámetro a.

a.map(m=>                       )

Asigne sobre la matriz, pasando cada cadena a través de una función, donde mestá la cadena actual.

 m[1]?

Compruebe si la cadena contiene un segundo segundo carácter ( "'"o "2").

+m[1]?

Si intenta convertir esa cadena de caracteres en un entero. Si la cadena es "2", se convierte 2, lo cual es verdadero. Si la cadena es "'", se convierte en NaNfalsey.

m

Si la prueba anterior es verdadera, simplemente regrese m.

:m[0]

De lo contrario, devuelve el primer carácter de m.

:m+"'"

Si la cadena no contiene un segundo carácter, regrese magregado con un '.

.reverse()

Invierta la matriz modificada.

Lanudo
fuente
Lo siento, acabo de ver esto. Mi propia respuesta es similar a la tuya: P
Conor O'Brien
2

Python ,  51  48 bytes

lambda a:[(v+"'")[:2-("'"in v)]for v in a[::-1]]

Una función sin nombre que toma y devuelve listas de cadenas.

Pruébalo en línea!

Invierte la lista de entrada con a[::-1]; agrega un 'a cada entrada con v+"'"; encabeza cada uno a 1 o 2 caracteres dependiendo de si el original tenía 'o no adentro [:2-("'"in v)].

Jonathan Allan
fuente
2

Python 3 , 91 89 72 70 69 65 bytes

lambda s:[i[0]+(len(i)-2and"'"or"2"*("2"==i[1]))for i in s[::-1]]

Pruébalo en línea! (Con estuches)

Aparentemente no necesita tomar la entrada y la salida como cadenas, por lo que es posible una solución de 69 bytes

sagiksp
fuente
AFAIK puedes borrar el espacio despuéslen(i)==1
Stephen
@StepHen Huh, no sabía que estaba permitido (sabía que algunos intérpretes lo permitían, simplemente no sabía que estaba permitido en codegolf)
sagiksp
2
Los idiomas están definidos por sus intérpretes aquí, por lo que, si funciona en cualquier intérprete, es válido.
Shaggy
Si el intérprete lo permite, puede hacerlo. Eso es todo lo que le importa al código golf;)
Stephen
len(i)-2es más corto que len(i)==1(recuerda 0 es falsey)
Stephen
1

Haskell , 43 bytes

map f.reverse
f[x]=x:"'"
f[x,c]=x:[c|c>'1']

Pruébalo en línea! Declara una función anónima map f.reverse. Enlace gy uso como g["S","T","A","C","K"].

Laikoni
fuente
1

PHP , 81 bytes

<?foreach(array_reverse($_GET)as$v)$r[]=$v[1]?$v[1]<2?$v[0]:$v:"$v'";print_r($r);

Pruébalo en línea!

Jörg Hülsermann
fuente
1

05AB1E , 13 bytes

RεÐ1èQ''si«ëK

Pruébalo en línea!

Explicación

RεÐ1èQ''si«ëK
R             # Reverse input array
 ε            # Map over each element...
  Ð1èQ         # Is the second char in the element the first one? (Uses the fact that in python indexing loops)
      ''       # Push '
        s      # Swap top items of stack
         i     # If the question above is true...
          «     # Concatenate
           ë   # Else
            K   # Push element without '  
Datboi
fuente
1

J, 25 bytes

J maneja esto bien, aparte de la desafortunada secuencia de escape necesaria para representar una cita simple:

|.,&''''`}:@.(''''={:)&.>

Necesitamos representar la lista usando datos en recuadro, ya que es una combinación de elementos de uno y dos caracteres, por lo tanto:

  • &.> - "debajo de unbox", que significa desempaquetar cada elemento, realice la operación que sigue (es decir, los símbolos que se explican a continuación) y luego vuelva a boxear cuando haya terminado
  • (''''={:) "si el segundo carácter es una cita simple" ....
  • @. (El verbo de agenda de J, una especie de declaración ternaria generalizada o una declaración de caso) "luego realice el segundo elemento de la lista de agenda, de lo contrario realice el primero"
  • }: (el segundo elemento de la lista de agenda), "eliminar el último carácter", es decir, la comilla simple
  • `(Verbo de corbata de J) Puede pensar en esto como el separador de elementos de la agenda
  • ,&'''' (primer elemento de la lista de la agenda) "agregue una sola cita al final"
  • |. "marcha atrás"

Pruébalo en línea!

Jonás
fuente
0

Java 8, 141 128 126 bytes

a->new StringBuffer(a.replaceAll("(.)","$1'").replace("'''","").replaceAll("(.)'","'$1").replaceAll("'(.)'2","2$1")).reverse()

Toma la entrada como única Stringsin espacios (es decir RUR'URU2R'U).

Explicación:

Pruébalo en línea.

a->new StringBuffer(           // Method with String parameter and StringBuffer return-type
  a.replaceAll("(.)","$1'")    //1  Add an apostrophe after every character
   .replace("'''","")          //2  Remove all occurrences of three adjacent apostrophes
   .replaceAll("(.)'","'$1")   //3  Reverse letter+apostrophe to apostrophe+letter
   .replaceAll("'(.)'2","2$1") //4  Reverse letter+2 to 2+letter and remove aphostrophes
  ).reverse()                  //5 Reverse everything

Ejemplo de los pasos anteriores, con la entrada dada: RUR'URU2R'U

  1. RUR'URU2R'UR'U'R'''U'R'U'2'R'''U'
  2. R'U'R'''U'R'U'2'R'''U'R'U'RU'R'U'2'RU'
  3. R'U'RU'R'U'2'RU''R'UR'U'R'U'2R'U
  4. 'R'UR'U'R'U'2R'U'R'UR'U'R2UR'U
  5. 'R'UR'U'R2UR'UU'RU2R'U'RU'R'
Kevin Cruijssen
fuente