Sigue el camino

18

El desafío es seguir (dibujar) el camino:

  • ^n - arriba por n líneas
  • vn - abajo por n líneas
  • >n - justo por n posiciones de caracteres
  • <n - dejado por n posiciones de caracteres

  • n es un número entero mayor que cero (es decir, no puede recibir un comando como >-2 ).
  • No hay separadores entre los comandos, la entrada bien formada se ve así: >5v8<10^3 no se permite ninguna otra forma de entrada.
  • El número de comandos es ilimitado.
  • Se supone que no se arrastran más caracteres en la entrada.

Ejemplos.

  1. La entrada es una cadena vacía, salida:

    *
    
  2. La entrada es >3o <3: tenga en cuenta que esto no hace ninguna diferencia en la salida:

    ****
    
  3. Similar para ^3y v3:

    *
    *
    *
    *
    
  4. Entrada: >1v2salida:

    **
     *
     *
    
  5. Entrada: ^4>3v2<1salida:

    ****
    *  *
    * **
    *
    *
    
  6. Si regresa y usa el mismo camino, no dibuje nada nuevo. P.ej>5<5

    ******
    
  7. ... aunque no dibujas nada nuevo, obviamente cambias de posición. Por lo tanto, si su entrada se ve así: >4<2v3la salida es:

    *****
      *
      *
      *
    
  8. Este es un ejemplo más complejo: 1) el camino puede cruzarse solo 2) tenga en cuenta que los últimos tres pasos del último comando desplazan todo el camino hacia la derecha. Entrada: v6>4^3<7salida:

       *
       *
       *
    ********
       *   *
       *   *
       *****
    
  9. Entrada :

    ^2v2>3<3v3>4^5v5>3^5>4v2<4v3>4^3v3>3^5>4v2<4v3>7^5>4v2<4v3>9^3<2^2v2>4^2v2<2v3>8^5>2v4>2^4v5<3>6^5>5<5v2>5<5v2>5<4v1>8^3<1^2v2>1v2>2^3v3>2^2>1^2v2<1v3<3>11^3<2^2v2>4^2v2<2v3>5^5>5<5v2>5<5v2>5<4v1>7^5>4v2<4v3>4^3v3>3^5>4v2<3v1<1v2>3^1>1v1
    

    Salida:

    *   *  *****  *****  *****  *   *     *** *  ******  *     *    *   *  ******  *****  *****
    *   *  *   *  *   *  *   *  *   *     * * *  *       *  *  *    *   *  *       *   *  *   *
    *****  *****  *****  *****  *****     * * *  ******  ** * **    *****  ******  *****  *****
    *   *  *   *  *      *        *       * * *  *        * * *       *    *       *   *  **
    *   *  *   *  *      *        *       * ***  ******   *****       *    ******  *   *  *  **
    *******************************************************************************************
    
nicael
fuente
66
A medida que han publicado este reto hoy en día, creo que esto va a ser un caso de prueba adecuado: ^2v2>3<3v3>4^5v5>3^5>4v2<4v3>4^3v3>3^5>4v2<4v3>7^5>4v2<4v3>9^3<2^2v2>4^2v2<2v3>8^5>2v4>2^4v5<3>6^5>5<5v2>5<5v2>5<4v1>8^3<1^2v2>1v2>2^3v3>2^2>1^2v2<1v3<3>11^3<2^2v2>4^2v2<2v3>5^5>5<5v2>5<5v2>5<4v1>7^5>4v2<4v3>4^3v3>3^5>4v2<3v1<1v2>3^1>1v1.
insertusernamehere
¿Podría posiblemente proporcionar una implementación de referencia?
LegionMammal978
¿No es eso realmente un engaño? Por favor decida: D
nicael
@nicael: Yo diría que no lo es; la E / S es diferente y parece que los caminos no pueden cruzarse en el otro. Creo que este es más simple en formas que podrían permitir diferentes estrategias de golf. Sin embargo, no sabía que de repente pude volver a abrir todo esto solo, pensé que simplemente estaba emitiendo un voto.
marinus
@marinus Ok, entonces. Entonces, relacionado: ¡Yarr! Un mapa del tesoro escondido! .
nicael

Respuestas:

2

MATL , 71 bytes

1thj'.\d+'XX"@Z)XK6L)U:"K1)XK118=K94=-K62=K60=-hv]]YstY)X<1--lqg10*32+c

Utiliza la versión actual (6.0.0) del lenguaje / compilador. Trabaja en Matlab y en Octave.

EDITAR (21 de junio de 2016): debido a cambios en el idioma, el código requiere algunas modificaciones para ejecutarse en la versión actual (16.0.0). Puede probarlo en línea, incluidas las modificaciones necesarias.

Ejemplos

>> matl
 > 1thj'.\d+'XX"@Z)XK6L)U:"K1)XK118=K94=-K62=K60=-hv]]YstY)X<1--lqg10*32+c
 > 
> ^4>3v2<1
    ****
    *  *
    * **
    *   
    *  

>> matl
 > 1thj'.\d+'XX"@Z)XK6L)U:"K1)XK118=K94=-K62=K60=-hv]]YstY)X<1--lqg10*32+c
 > 
> ^2v2>3<3v3>4^5v5>3^5>4v2<4v3>4^3v3>3^5>4v2<4v3>7^5>4v2<4v3>9^3<2^2v2>4^2v2<2v3>8^5>2v4>2^4v5<3>6^5>5<5v2>5<5v2>5<4v1>8^3<1^2v2>1v2>2^3v3>2^2>1^2v2<1v3<3>11^3<2^2v2>4^2v2<2v3>5^5>5<5v2>5<5v2>5<4v1>7^5>4v2<4v3>4^3v3>3^5>4v2<3v1<1v2>3^1>1v1
  *   *  *****  *****  *****  *   *     *** *  ******  *     *    *   *  ******  *****  *****
  *   *  *   *  *   *  *   *  *   *     * * *  *       *  *  *    *   *  *       *   *  *   *
  *****  *****  *****  *****  *****     * * *  ******  ** * **    *****  ******  *****  *****
  *   *  *   *  *      *        *       * * *  *        * * *       *    *       *   *  **   
  *   *  *   *  *      *        *       * ***  ******   *****       *    ******  *   *  *  **
  ******************************************************************************************* 

Explicación

El programa tiene cuatro pasos principales:

  1. Lea la cadena de entrada y divídala en sus componentes.
  2. Construya una matriz de 2 columnas donde cada fila describa un desplazamiento unitario en la dirección apropiada. Por ejemplo, [0 -1]indica un paso a la izquierda. La primera fila es el origen de la ruta,[1 1]
  3. Calcule la suma acumulativa de esa matriz a lo largo de la primera dimensión. Ahora cada fila describe las coordenadas de a *. Normalizar a valor mínimo1
  4. Cree una nueva matriz que contenga 1las coordenadas indicadas por la matriz del paso 3, y de lo 0contrario. Esto luego se transforma en una matriz de caracteres.

Código:

1th                         % row vector [1 1]. Initiallize matrix of step 2
j                           % (step 1) read input string 
'.\d+'XX                    % split into components. Creates cell array of substrings
"                           % (step 2) for each component
   @Z)XK                    % unbox to obtain substring and copy
   6L)U:                    % obtain number and build vector of that size
   "                        % repeat as many times as that number
      K1)                   % paste substring. Get first character: '^', 'v', '>', '<'
      XK118=K94=-           % vertical component of unit displacement: -1, 0 or 1
      K62=K60=-             % horizontal component of unit displacement: -1, 0 or 1
      h                     % concatenate horizontally
      v                     % append vertically to existing matrix
   ]                        % end
]                           % end
Ys                          % (step 3) cumulative sum along first dimension
tY)X<1--                    % normalize to minimum value 1
lqg                         % (step 4) build matrix with 0/1
10*32+c                     % replace 0 by space and 1 by asterisk
Luis Mendo
fuente
¿Funciona para el último ejemplo?
nicael
¡Que agradable! Si lo hace. He editado mi respuesta para incluirla
Luis Mendo
8

JavaScript (ES6), 204 211 210

Edición 1 Corrección de errores: salida '*' para entrada nula
Edición 2 Decodificación más simple de dirección a diferencias de x e y

Aquí está mi respuesta a El mapa del tesoro , revisado para cumplir con las especificaciones.

F=m=>(m.replace(/\D(\d+)/g,(d,z)=>{for(;z--;r=[...r],r[x]=m,p[y]=r.join``)for(d<'>'?--x:d<'^'?++x:d<'v'?--y:++y,p=~x?~y?p:[y=0,...p]:p.map(r=>' '+r,x=0),r=p[y]||'';!r[x];)r+=' '},x=y=0,p=[m='*']),p.join`
`)

Menos golf y explicado más o menos

f=m=>(
  x=y=0, // starting position
  p=['*'], // output string array (initialized with minimum output)
  m.replace( /\D(\d+)/g, 
  (d,z) => // execute the following for each group direction/length. Length in z, direction in d[0]
  {
    while( z--)  // repeat for the len
    {
      // check d to change values of x and y
      // all the comparison are with > and <, not equal
      // so that they work with the whole d, not just d[0]
      d<'>'?--x:d<'^'?++x:d<'v'?--y:++y,
      // now if x or y are < 0 then p must be adjusted  
      p = ~x 
        ? ~y
          ? p // both x and y are >= 0, p is not changed
          : [y = 0, ...p] // y < 0, shift p by on adding a 0 element and set y to 0
        : p.map(r=> ' ' + r, x = 0); // x < 0, add a space to the left for each row in p and set x to 0
      r = p[y] || ''; // get current row in r
      for( ; !r[x]; ) // if the current row is empty or too short
        r += ' '; // ... add spaces up to position x
      // set character in x position
      r = [...r], // the shorter way is converting to array ...
      r[x] = '*', // setting the element
      p[y] = r.join`` // and the back to string using join
    }
  }),
  p.join`\n` // return output array as a newline separated string
}

Prueba

F=m=>(m.replace(/\D(\d+)/g,(d,z)=>{for(;z--;r=[...r],r[x]='*',p[y]=r.join``)for(d<'>'?--x:d<'^'?++x:d<'v'?--y:++y,p=~x?~y?p:[y=0,...p]:p.map(r=>' '+r,x=0),r=p[y]||'';!r[x];)r+=' '},x=y=0,p=['*']),p.join`
`)

// TEST
console.log = x => O.textContent += x + '\n';

console.log(F('')+'\n')

console.log(F('v6>4^3<7')+'\n')

console.log(F('^2v2>3<3v3>4^5v5>3^5>4v2<4v3>4^3v3>3^5>4v2<4v3>7^5>4v2<4v3>9^3<2^2v2>4^2v2<2v3>8^5>2v4>2^4v5<3>6^5>5<5v2>5<5v2>5<4v1>8^3<1^2v2>1v2>2^3v3>2^2>1^2v2<1v3<3>11^3<2^2v2>4^2v2<2v3>5^5>5<5v2>5<5v2>5<4v1>7^5>4v2<4v3>4^3v3>3^5>4v2<3v1<1v2>3^1>1v1'))
<pre id=O></pre>

edc65
fuente
Parece funcionar perfectamente.
nicael
Con una única excepción: cuando la entrada está vacía, el requisito es escribir *.
nicael
Para los navegadores que tienen problemas para interpretar ES6: jsfiddle.net/2vrrd1wt .
nicael
@nicael gracias por notarlo. Corregido por 1 byte
edc65
1

Perl, 174 bytes

@M=(['*']);pop=~s/(.)(\d+)/($z=ord$1)&64?($y+=$z&8?-1:1)<0&&unshift@M,[$y++]:($x+=($z&2)-1)<0?@M=map{[$x=0,@$_]}@M:0,$M[$y][$x]='*'for1..$2/gre;print map{map{$_||$"}@$_,$/}@M

Espera entrada como argumento de línea de comandos. ¡Asegúrese de citar el argumento!
Ejemplo:perl 177.pl "<1^2>3v4<5^6>7v8<9^10>11"

Algo legible:

@M=(['*']);                                 # output origin/starting position

pop=~                                       # apply regex to cmdline arg
s!(.)(\d+)!                                 # match $1=direction, $2=count

    ($z=ord$1)                              # get ASCII code for char
    &64                                     # 'v^' have this bit set, '<>' don't

        ?                                   # adjust y:
            ($y += $z&8 ? -1 : 1)           # '^' has bit set, 'v' doesn't
            < 0 &&                          # negative y?
            unshift @M, [$y++]              # prepend row; abuse [] for $y++ saving 3 bytes

        :                                   # adjust x:
            ($x+= ($z&2) -1 )               # '>' has bit set: 2-1=1, '<' hasn't: 0-1=-1
            < 0 ?                           # negative x?
                @M = map{ [$x=0,@$_] } @M   # prepend column, reset x
                :0                          # '?:0' shorter than '&&()'
        ,                                   # oh, and also:
        $M[$y][$x]='*'                      # output current position.

    for 1..$2                               # iterate count
!grex;                                      

print map{ map{$_||$"} @$_, $/ } @M         # iterate rows/cols, print '*' or space
Kenney
fuente