Rotor Routers on a Grid Input

Your input is a single string, separated by newlines into 2n+1 lines of length 2n+1, for some integer n &ge; 0. The integer n is not part of the input; you'll have to compute it from the string. The lines are composed of the "direction characters" &gt;^&lt;v. If newlines pose a problem, you can replace them by vertical pipes |.

The input forms a square grid of size (2n+1)x(2n+1), and each cell of the grid is interpreted as a rotor router, which points in one of the four cardinal directions. We proceed to drop a token on the router at the center of the grid, and then the routers will move it around in the following way. When the token lands on a router, the router turns 90 degrees in the counter-clockwise direction, and moves the token one step in the new direction it points to. If it lands on another router, the process is repeated, but eventually, the token will fall off the grid.

Output

Your output is the final configuration of the routers, in the same format as the input.

Example

As an example input, consider the 3x3 grid

&lt;^&lt;
^>&lt;
>^v


where the central router has been highlighted to indicate the token (it's a bit hard to see). The central router rotates to face north, and moves the token to the central cell of the top row:

&lt;^&lt;
^^&lt;
>^v


This router rotates to face west, and sends the token to the top left corner:

&lt;&lt;&lt;
^^&lt;
>^v


The router in the corner sends the token south, so it's now at the leftmost cell of the middle row:

v&lt;&lt;
^^&lt;
>^v


That router rotates to face west and sends the token off the grid.

v&lt;&lt;
&lt;^&lt;
>^v


This is the final grid configuration, so your program should output it. Note that in more complex examples, the token can pass the same router multiple times before falling off the grid.

Rules

You can write either a function or a full program. This is code-golf, so the lowest byte count wins. Standard loopholes are disallowed. You can decide whether there is a trailing newline in the input and/or output.

Test Cases

Input:
v
Output:
&gt;

Input:
&lt;^&lt;
^&gt;&lt;
&gt;^v
Output:
v&lt;&lt;
&lt;^&lt;
&gt;^v

Input:
&gt;&gt;^&gt;&gt;
v&lt;vv&lt;
&gt;^&gt;^&lt;
^&lt;&gt;&gt;^
vvv&gt;&gt;
Output:
&gt;&gt;^&gt;&gt;
&gt;v&gt;&gt;v
^&gt;&gt;vv
^^&gt;&gt;&gt;
v^&lt;&lt;^

Input:
&lt;^^^^^^^^
&lt;&lt;^^^^^^&gt;
&lt;&lt;&lt;^^^^&gt;&gt;
&lt;&lt;&lt;&lt;^^&gt;&gt;&gt;
&lt;&lt;&lt;&lt;^&gt;&gt;&gt;&gt;
&lt;&lt;&lt;vv&gt;&gt;&gt;&gt;
&lt;&lt;vvvv&gt;&gt;&gt;
&lt;vvvvvv&gt;&gt;
vvvvvvvv&gt;
Output:
&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;v
^&gt;&gt;&gt;&gt;&gt;&gt;vv
^^&gt;&gt;&gt;&gt;vvv
^^^&gt;&gt;vvvv
&lt;&lt;&lt;&lt;&lt;vvvv
^^^^&lt;&lt;vvv
^^^&lt;&lt;&lt;&lt;vv
^^&lt;&lt;&lt;&lt;&lt;&lt;v
^&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;
CJam, 62 61 63 bytes

Try it online

Nq_N#):D;+_,2/{:P"^&lt;v&gt;^

"_P4$=#:X)=t_,0PX[1DW*WDSP]=-e&gt;e&lt;}h;1&gt;


Expanded and commented:

Nq              "Read the input grid";
_N#):D;         "Calculate the vertical delta (line length + 1)";
+               "Prepend a newline to the grid";
_,2/            "Calculate the initial position as the length of the grid
                 string divided by 2";
{               "Do...";
  :P"^&lt;v&gt;^

"
  _P4$=           "Get the character indexed by the position in the grid";
  #:X             "Map the character to an operation number:
                   '^'=&gt;0, '&lt;'=&gt;1, 'v'=&gt;2, '&gt;'=&gt;3, '^'=&gt;4, '\n'=&gt;5, '\n'=&gt;6
                   (the unreachable duplicate mappings are important below)";
  )=t             "Set the character indexed by the position in the grid to
                   the result of mapping the operation number + 1 backwards";
  _,0PX[1DW*WDSP]="Map the operation number to a negated delta (this occurs
                   after rotating routers, which means that operation n should
                   act like the character corresponding to operation n + 1):
                   0=&gt;1, 1=&gt;-delta, 2=&gt;-1, 3=&gt;delta, 5=&gt;position";
  -e&gt;e&lt;           "Subtract the negated delta from the position and clamp it to
                   [0, length of the grid string] (array indices are circular,
                   so the length of the grid string will act like the index 0
                   and point to the initial newline next iteration, which will
                   *really* set the position to 0)";
}h              "... while the position is not 0 (i.e. not at the initial
                 newline)";
;1&gt;             "Clean up and remove the initial newline";


My solution operates on the input as a flat string, so there's only one position value to keep track of and virtually no pre/postprocessing; there are only 2 bytes of preprocessing to add newline to the beginning of the grid and 2 bytes of postprocessing to remove it from the output. But these 4 bytes are well worth the cost as they let me keep newlines in and "execute" them like routers, but they "rotate" into another newline and set the position to zero. And the main loop ends when the position becomes zero.