Problem:
A さんと B 君は，
N
×
M
の長方形のマス目状の地域に住んでいる．各マス目は道か壁か家のどれかである．この地域は，道が複雑で入り組んでいるので痴漢被害がよく起こることで有名であるため，この地域と外部との境界は全て壁で囲まれており，隔離されている．
B 君はなんとなく気が向いたので，A さんの家を眺めに行くことにした．しかし，不幸なことにB 君は明らかに怪しい顔をしているので，A さんの家に行く途中に少しでも痴漢の疑いがあるような行動を取ったらすぐに捕まってしまうだろう．特に，右手を壁から離して歩くことは絶対にやってはならない．B 君は，一瞬たりとも右手を離すことなく，A さんの家に辿り着くことが出来るだろうか？
B 君はつねに上下左右いずれかの方向を向いていて，B 君の右手が届く範囲はB 君の向いている方向に対して正面，斜め右前，右，斜め右後ろの4 マスのみである．B 君は，次のいずれかの行動を繰り返す．ただし，これらを同時に行うことは出来ない．
前方に壁がない場合，1 マス進む．
向いている方向を90 度右に変える．
向いている方向を90 度左に変える．
右手が接するマスを変える．ただし，この時にB 君は右手を離すことが出来ないので，変更前のマスと変更後のマスの間には共通した点を持っていなくてはならない．
Input
入力は以下の形式で与えられる．
N
M
S
1
S
2
:
S
N
S
i
(1 ≤
i
≤
N
) は，
M
文字の文字列で各文字は次を表す．
"^"，"v"，"<"，">" は B 君の最初の位置と最初に向いている方向（上下左右の向き）を表す．
"." は，何もないマスである．B 君は，このマスの上を移動することができる．
"#" は，壁を表す．壁の上を移動することは出来ない．
"G" は A さんの家の位置を表す．B 君は，A さんの家にたどり着くまで移動を繰り返す．
Constraints
1 ≤
N
≤ 50
1 ≤
M
≤ 50
入力には，文字 "^"，"v"，"<"，">" のうちいずれかが必ず一つのみ現れる．
同様に，入力には，文字 "G" が必ず一つのみ現れる．
初期状態では，B 君が向いている方向から右の壁にB 君の右手が接している．
Output
一度も右手を離さずにA さんの家に辿り着くことが出来る場合には，A さんの家にたどり着くまでに通った異なるマスの数の最小値を出力せよ．A さんの家に辿り着くことが出来ない場合には，-1 を出力せよ．
Sample Input 1
3 3
G##
.#.
.<.
Output for the Sample Input 1
4
Sample Input 2
3 3
G##
.#.
.>.
Output for the Sample Input 2
6
Sample Input 3
3 3
...
.G.
.>.
Output for the Sample Input 3
-1
Sample Input 4
4 4
....
.#.G
...#
^#..
Output for the Sample Input 4
8

Submitted solutions:

code_snippet: #include <bits/stdc++.h>




namespace zawa {

using i16 = std::int16_t;
using i32 = std::int32_t;
using i64 = std::int64_t;
using i128 = __int128_t;

using u8 = std::uint8_t;
using u16 = std::uint16_t;
using u32 = std::uint32_t;
using u64 = std::uint64_t;

using usize = std::size_t;

} // namespace zawa


namespace zawa {

void SetFastIO() {
    std::cin.tie(nullptr)->sync_with_stdio(false);
}

void SetPrecision(u32 dig) {
    std::cout << std::fixed << std::setprecision(dig);
}

} // namespace zawa
using namespace zawa;

int dx[4]{ -1, 0, 1, 0 }, dy[4]{ 0, 1, 0, -1 };
int rx[3][4]{ { -1, 1, 1, -1 }, { 0, 1, 0, -1 }, { 1, 1, -1, -1 } };
int ry[3][4]{ { 1, 1, -1, -1 }, { 1, 0, -1, 0 }, { 1, -1, -1, 1 } };

int main() {
    SetFastIO();

    int N, M;
    std::cin >> N >> M;
    std::vector<std::string> S(N);
    for (auto& s : S) std::cin >> s;
    int curx{-1}, cury{-1}, dir{-1};
    auto f{[&](int dir, int x, int y) -> int {
        return dir * N * M + x * M + y;
    }};
    std::vector<bool> vis(4 * N * M);
    for (int i{} ; i < N ; i++) {
        for (int j{} ; j < M ; j++) {
            if (S[i][j] == '^') {
                curx = i;
                cury = j;
                dir = 0;
            }
            if (S[i][j] == '>') {
                curx = i;
                cury = j;
                dir = 1;
            }
            if (S[i][j] == 'v') {
                curx = i;
                cury = j;
                dir = 2;
            }
            if (S[i][j] == '<') {
                curx = i;
                cury = j;
                dir = 3;
            }
        }
    }
    vis[f(dir, curx, cury)] = true;
    auto in{[&](int x, int y) -> bool {
        return 0 <= x and x < N and 0 <= y and y < M;
    }};
    auto isWall{[&](int x, int y) -> bool {
        return !in(x, y) or S[x][y] == '#';
    }};
    auto valid{[&](int dir, int x, int y) -> int {
        assert(!isWall(x, y));
        int res{};
        for (int i{} ; i < 3 ; i++) {
            int nx{x + rx[i][dir]}, ny{y + ry[i][dir]};
            if (isWall(nx, ny)) res |= (1 << i);
        }
        return res;
    }};
    int hand{1};
    int cnt{10000000};
    for (int _{} ; _ < cnt and S[curx][cury] != 'G' ; _++) {
        // std::cout << curx << ' ' << cury << ' ' << hand << std::endl;
        int nx{curx + dx[dir]}, ny{cury + dy[dir]};
        if (hand == 0) {
            if (!isWall(nx, ny)) {
                curx = nx;
                cury = ny;
                hand = 1;
            }
            else {
                dir = (dir + 3) % 4;
                hand = 1;
            }
        }
        else if (hand == 1) {
            if (!isWall(nx, ny)) {
                curx = nx;
                cury = ny;
                if (valid(dir, curx, cury) & (1 << 1)) {
                    hand = 1;
                }
                else {
                    hand = 2;
                }
            }
            else {
                // assert(valid(dir, curx, cury) & (1 << 0));
                dir = (dir + 3) % 4;
                hand = 1;
            }
        }
        else if (hand == 2) {
            dir = (dir + 1) % 4;
            hand = 0;
        }
        else {
            assert(!"hand invalid");
        }
        // if (vis[f(dir, curx, cury)]) break;
        vis[f(dir, curx, cury)] = true;
    }
    if (S[curx][cury] != 'G') {
        std::cout << -1 << '\n';
    }
    else {
        int ans{};
        for (int i{} ; i < N ; i++) {
            for (int j{} ; j < M ; j++) {
                bool fl{};
                for (int d{} ; d < 4 ; d++) {
                    fl |= vis[f(d, i, j)];
                }
                ans += fl;
            }
        }
        std::cout << ans << '\n';
    }
}
accuracy: 1
time_ms: 70
memory_kb: 3472
final_rank: 5

code_snippet: #include <bits/stdc++.h>
using namespace std;

#define int long long

int dx[4] = {0, 1, 0, -1}, dy[4] = {-1, 0, 1, 0};
int H, W;
char grid[55][55];
bool used[55][55];

int x, y, d;

signed main() {
    cin >> H >> W;
    for ( int i = 0; i < H+2; i++ )
        for ( int j = 0; j < W+2; j++ ) grid[i][j] = '#';

    for ( int i = 1; i <= H; i++ )
        for ( int j = 1; j <= W; j++ ) {
            cin >> grid[i][j];
            if ( grid[i][j] == '^' ) {
                x = j; y = i; d = 0;
            }
            if ( grid[i][j] == 'v' ) {
                x = j; y = i; d = 2;
            }
            if ( grid[i][j] == '>' ) {
                x = j; y = i; d = 1;
            }
            if ( grid[i][j] == '<' ) {
                x = j; y = i; d = 3;
            }
        }

    int cnt = 0;
    while ( cnt++ < 10000000 ) {
        used[y][x] = true;
        int nx = x+dx[d], ny = y+dy[d];
        int wx = nx+dx[(d+1)%4], wy = ny+dy[(d+1)%4];
        if ( grid[y][x] == 'G' ) {
            int ans = 0;
            for ( int i = 1; i <= H; i++ ) {
                for ( int j = 1; j <= W; j++ ) {
                    if ( used[i][j] ) ans++;
                }
            }
            cout << ans << endl;            
            return 0;
        }

        if ( grid[ny][nx] == 'G' ) {
            int ans = 0;
            for ( int i = 1; i <= H; i++ ) {
                for ( int j = 1; j <= W; j++ ) {
                    if ( used[i][j] ) ans++;
                }
            }
            cout << ans+1 << endl;            
            return 0;
        }

        if ( grid[ny][nx] != '#' && grid[wy][wx] == '#' ) { // chokusin
            x = nx; y = ny;            
        }
        else if ( grid[ny][nx] != '#' && grid[wy][wx] != '#' ) { // ukai
            used[ny][nx] = true;            
            x = wx; y = wy;
            d = (d+1)%4;
        } else {
            d = (d-1+4)%4;            
        }
    }

    cout << -1 << endl;    
    
    
    return 0;
}
accuracy: 1
time_ms: 30
memory_kb: 3136
final_rank: 2

code_snippet: #include <bits/stdc++.h>
using namespace std;

#define int long long

int dx[4] = {0, 1, 0, -1}, dy[4] = {-1, 0, 1, 0};
int H, W;
char grid[55][55];
bool used[55][55];

int x, y, d;

signed main() {
    cin >> H >> W;
    for ( int i = 0; i < H+2; i++ )
        for ( int j = 0; j < W+2; j++ ) grid[i][j] = '#';

    for ( int i = 1; i <= H; i++ )
        for ( int j = 1; j <= W; j++ ) {
            cin >> grid[i][j];
            if ( grid[i][j] == '^' ) {
                x = j; y = i; d = 0;
            }
            if ( grid[i][j] == 'v' ) {
                x = j; y = i; d = 2;
            }
            if ( grid[i][j] == '>' ) {
                x = j; y = i; d = 1;
            }
            if ( grid[i][j] == '<' ) {
                x = j; y = i; d = 3;
            }
        }

    int cnt = 0;
    while ( cnt++ < 10000000 ) {
        used[y][x] = true;
        if ( grid[y][x] == 'G' ) {
            int ans = 0;
            for ( int i = 1; i <= H; i++ ) {
                for ( int j = 1; j <= W; j++ ) {
                    if ( used[i][j] ) ans++;
                }
            }
            cout << ans << endl;            
            return 0;
        }

        int nx = x+dx[d], ny = y+dy[d];
        int wx = nx+dx[(d+1)%4], wy = ny+dy[(d+1)%4];

        if ( grid[ny][nx] != '#' && grid[wy][wx] == '#' ) { // chokusin
            x = nx; y = ny;            
        }
        else if ( grid[ny][nx] != '#' && grid[wy][wx] != '#' ) { // ukai
            used[ny][nx] = true;            
            x = wx; y = wy;
            d = (d+1)%4;
        } else {
            d = (d-1+4)%4;            
        }
    }

    cout << -1 << endl;    
    
    
    return 0;
}
accuracy: 0.2833333333333333
time_ms: 30
memory_kb: 3108
final_rank: 17

code_snippet: #include <iostream>
#include <algorithm>
#include <vector>
#include <string>

using Int = long long int;
using Char = char;
using String = std::string;
template <class T>
using Vector = std::vector<T>;

int main() {
    Int h, w;
    std::cin >> h >> w;
    Int n = std::max(h, w) + 2;

    Vector<String> s(n, String(n, '#'));
    for (Int x = 1; x <= h; ++x) {
        for (Int y = 1; y <= w; ++y) {
            std::cin >> s[x][y];
        }
    }

    Int x, y;
    auto search = [&] {
        for (x = 0; x < n; ++x) {
            for (y = 0; y < n; ++y) {
                if (s[x][y] != '#' &&
                    s[x][y] != '.' &&
                    s[x][y] != 'G' &&
                    s[x][y] != 'o') return;
            }
        }
    };

    auto rotateL = [&] {
        for (Int i = 0; i < n; ++i) {
            for (Int j = 0; j < i; ++j) {
                std::swap(s[i][j], s[j][i]);
            }
        }
        std::reverse(s.begin(), s.end());
        search();
    };

    auto rotateR = [&] {
        std::reverse(s.begin(), s.end());
        for (Int i = 0; i < n; ++i) {
            for (Int j = 0; j < i; ++j) {
                std::swap(s[i][j], s[j][i]);
            }
        }
        search();
    };

    search();
    {
        Char dir = s[x][y];
        s[x][y] = '^';
        if (dir == '>') {
            rotateL();
        } else if (dir == '<') {
            rotateR();
        } else if (dir == 'v') {
            rotateL(), rotateL();
        }
    }

    /*
    std::cerr << "begin" << '(' << x << ',' << y << ')' << std::endl;
    for (auto& v : s) {
        std::cerr << v << std::endl;
    }
    */

    for (Int t = 0; t < n * n * 10; ++t) {
        if (s[x - 1][y] == '#') {
            rotateR();
        } else {
            s[x][y] = 'o';
            --x;
            if (s[x][y] == 'G') break;
            s[x][y] = '^';

            if (s[x][y + 1] != '#') rotateL();
        }

        /*
        std::cerr << t << '(' << x << ',' << y << ')' << std::endl;
        for (auto& v : s) {
            std::cerr << v << std::endl;
        }
        */
    }

    Int ans = -1;
    if (s[x][y] == 'G') {
        s[x][y] = 'o';
        ans = 0;
        for (auto& v : s) ans += std::count(v.begin(), v.end(), 'o');
    }

    std::cout << ans << std::endl;
    return 0;
}
accuracy: 1
time_ms: 70
memory_kb: 3184
final_rank: 3

code_snippet: #if __has_include("../library/Basic/Debug.hpp")

#include "../library/Basic/Debug.hpp"

#else

/* ----- Header Files ----- */
// IO
#include <cstdio>
#include <iomanip>
#include <ios>
#include <iostream>

// algorithm
#include <algorithm>
#include <cmath>
#include <numeric>

// container
#include <vector>
#include <string>
#include <tuple>
#include <set>
#include <map>
#include <stack>
#include <queue>
#include <deque>

// others
#include <random>
#include <limits>
#include <functional>
#include <ctime>
#include <cassert>
#include <cstdint>


/* ----- Type Alias ----- */
using Bool = bool;
using Int = long long int;
using Real = long double;
using Char = char;
using String = std::string;
template <class... Ts>
using Tuple = std::tuple<Ts...>;

template <class T>
using Vector = std::vector<T>;
template <class T>
using Matrix = Vector<Vector<T>>;
template <class T>
using Queue = std::queue<T>;
template <class T>
using Stack = std::stack<T>;
template <class T>
using Deque = std::deque<T>;

template <class T>
using MaxHeap = std::priority_queue<T>;
template <class T>
using MinHeap = std::priority_queue<T, std::vector<T>, std::greater<T>>;
template <class T>
using Set = std::set<T>;
template <class T, class U>
using Map = std::map<T, U>;

template <class T, class... Us>
using Func = std::function<T(Us...)>;

template <class T>
T genv(T v) { return v; }

template <class T, class... Ts>
auto genv(size_t l, Ts... ts) {
    return Vector<decltype(genv<T>(ts...))>(l, genv<T>(ts...));
}

template <class Cost = Int>
struct Edge {
    Int src, dst;
    Cost cost;
    Edge(Int src = -1, Int dst = -1, Cost cost = 1)
        : src(src), dst(dst), cost(cost){};

    bool operator<(const Edge<Cost>& e) const { return this->cost < e.cost; }
    bool operator>(const Edge<Cost>& e) const { return this->cost > e.cost; }
};

template <class Cost = Int>
using Edges = Vector<Edge<Cost>>;
template <class Cost = Int>
using Graph = Vector<Vector<Edge<Cost>>>;

#endif

/* ----- Misc ----- */
void fastio() {
    std::ios::sync_with_stdio(false);
    std::cin.tie(nullptr);
}

struct Fout {
    Int precision;
    Fout(Int precision) : precision(precision) {}
};
std::ostream& operator<<(std::ostream& os, const Fout& fio) {
    os << std::fixed << std::setprecision(fio.precision);
    return os;
}


/* ----- Constants ----- */
// constexpr Int INF = std::numeric_limits<Int>::max() / 3;
// constexpr Int MOD = 1000000007;
// constexpr Real PI = acos(-1);
// constexpr Real EPS = 1e-10;
// std::mt19937 mt(int(std::time(nullptr)));

int main() {
    Int h, w;
    std::cin >> h >> w;
    Int n = std::max(h, w) + 2;

    Vector<String> s(n, String(n, '#'));
    for (Int x = 1; x <= h; ++x) {
        for (Int y = 1; y <= w; ++y) {
            std::cin >> s[x][y];
        }
    }

    auto rotateL = [&] {
        for (Int x = 0; x < n; ++x) {
            for (Int y = 0; y < x; ++y) {
                std::swap(s[x][y], s[y][x]);
            }
        }
        std::reverse(s.begin(), s.end());
    };

    auto rotateR = [&] {
        std::reverse(s.begin(), s.end());
        for (Int x = 0; x < n; ++x) {
            for (Int y = 0; y < x; ++y) {
                std::swap(s[x][y], s[y][x]);
            }
        }
    };

    Int x, y;
    auto search = [&] {
        for (x = 0; x < n; ++x) {
            for (y = 0; y < n; ++y) {
                if (s[x][y] != '#' &&
                    s[x][y] != '.' &&
                    s[x][y] != 'G' &&
                    s[x][y] != 'o') return;
            }
        }
    };

    search();
    {
        Char dir = s[x][y];
        s[x][y] = '^';
        if (dir == '>') {
            rotateL();
        } else if (dir == '<') {
            rotateR();
        } else if (dir == 'v') {
            rotateL(), rotateL();
        }
    }
    search();

    /*
    std::cerr << "begin" << '(' << x << ',' << y << ')' << std::endl;
    for (auto& v : s) {
        std::cerr << v << std::endl;
    }
    */

    for (Int t = 0; t < n * n * 10; ++t) {
        if (s[x - 1][y] == '#') {
            rotateR(), search();
        } else {
            s[x][y] = 'o';
            --x;
            if (s[x][y] == 'G') break;
            s[x][y] = '^';

            if (s[x][y + 1] != '#') {
                rotateL(), search();
            }
        }

        /*
        std::cerr << t << '(' << x << ',' << y << ')' << std::endl;
        for (auto& v : s) {
            std::cerr << v << std::endl;
        }
        */
    }

    Int ans = -1;
    if (s[x][y] == 'G') {
        s[x][y] = 'o';
        ans = 0;
        for (auto& v : s) ans += std::count(v.begin(), v.end(), 'o');
    }

    std::cout << ans << std::endl;
    return 0;
}
accuracy: 1
time_ms: 70
memory_kb: 3192
final_rank: 4

code_snippet: #include <bits/stdc++.h>
using namespace std;
using vi=vector<int>;
using vvi=vector<vi>;
using vs=vector<string>;
using msi=map<string,int>;
using mii=map<int,int>;
using pii=pair<int,int>;
using vlai=valarray<int>;
using ll=long long;
#define rep(i,n) for(int i=0;i<n;i++)
#define range(i,s,n) for(int i=s;i<n;i++)
#define all(a) a.begin(),a.end()
#define rall(a) a.rbegin(),a.rend()
#define fs first
#define sc second
#define pb push_back
#define eb emplace_back
#define mp make_pair
#define INF 1e9
#define EPS 1e-9

int main(){
    int h,w;
    cin>>h>>w;
    vvi f(h+2,vi(w+2,1));
    vvi walk(h+2,vi(w+2,0));
    int gy,gx,y=0,x=0,v=0;
    range(i,1,h+1)range(j,1,w+1){
        char c;
        cin>>c;
        switch(c){
            case 'G': gy=i,gx=j,f[i][j]=0; break;
            case '.': f[i][j]=0;break;
            case '#': break;
            case '^': y=i,x=j,v=0,f[i][j]=0; break;
            case '>': y=i,x=j,v=1,f[i][j]=0; break;
            case 'v': y=i,x=j,v=2,f[i][j]=0; break;
            case '<': y=i,x=j,v=3,f[i][j]=0; break;
        }
    }
    walk[y][x]=1;
    rep(loop,9000000){//2646
        vvi vec={{-1,0},{0,1},{1,0},{0,-1}};
        if(f[y+vec[(v+1)%4][0]][x+vec[(v+1)%4][1]]==0){
            v=(v+1)%4;
            y+=vec[v][0], x+=vec[v][1];
            walk[y][x]=1;
        }else if(f[y+vec[v][0]][x+vec[v][1]]==1){
            v=(v+3)%4;
        }else{
            y+=vec[v][0],x+=vec[v][1];
            walk[y][x]=1;
        }
        if(y==gy&&x==gx){
            break;
        }
    }
    if(y==gy&&x==gx){
        int ans=0;
        rep(i,h+2)rep(j,w+2)ans+=walk[i][j];
        cout<<ans<<endl;
    }else cout<<-1<<endl;
    return 0;
}
accuracy: 1
time_ms: 1980
memory_kb: 3192
final_rank: 12

code_snippet: #include <bits/stdc++.h>
using namespace std;
using vi=vector<int>;
using vvi=vector<vi>;
using vs=vector<string>;
using msi=map<string,int>;
using mii=map<int,int>;
using pii=pair<int,int>;
using vlai=valarray<int>;
using ll=long long;
#define rep(i,n) for(int i=0;i<n;i++)
#define range(i,s,n) for(int i=s;i<n;i++)
#define all(a) a.begin(),a.end()
#define rall(a) a.rbegin(),a.rend()
#define fs first
#define sc second
#define pb push_back
#define eb emplace_back
#define mp make_pair
#define INF 1e9
#define EPS 1e-9

int main(){
    int h,w;
    cin>>h>>w;
    vvi f(h+2,vi(w+2,1));
    vvi walk(h+2,vi(w+2,0));
    int gy,gx,y=0,x=0,v=0;
    range(i,1,h+1)range(j,1,w+1){
        char c;
        cin>>c;
        switch(c){
            case 'G': gy=i,gx=j,f[i][j]=0; break;
            case '.': f[i][j]=0;break;
            case '#': break;
            case '^': y=i,x=j,v=0,f[i][j]=0; break;
            case '>': y=i,x=j,v=1,f[i][j]=0; break;
            case 'v': y=i,x=j,v=2,f[i][j]=0; break;
            case '<': y=i,x=j,v=3,f[i][j]=0; break;
        }
    }
    walk[y][x]=1;
    rep(loop,6000000){//2646
        vvi vec={{-1,0},{0,1},{1,0},{0,-1}};
        if(f[y+vec[(v+1)%4][0]][x+vec[(v+1)%4][1]]==0){
            v=(v+1)%4;
            y+=vec[v][0], x+=vec[v][1];
            walk[y][x]=1;
        }else if(f[y+vec[v][0]][x+vec[v][1]]==1){
            v=(v+3)%4;
        }else{
            y+=vec[v][0],x+=vec[v][1];
            walk[y][x]=1;
        }
        if(y==gy&&x==gx){
            break;
        }
    }
    if(y==gy&&x==gx){
        int ans=0;
        rep(i,h+2)rep(j,w+2)ans+=walk[i][j];
        cout<<ans<<endl;
    }else cout<<-1<<endl;
    return 0;
}
accuracy: 1
time_ms: 1200
memory_kb: 3192
final_rank: 10

code_snippet: #include <bits/stdc++.h>
using namespace std;
using vi=vector<int>;
using vvi=vector<vi>;
using vs=vector<string>;
using msi=map<string,int>;
using mii=map<int,int>;
using pii=pair<int,int>;
using vlai=valarray<int>;
using ll=long long;
#define rep(i,n) for(int i=0;i<n;i++)
#define range(i,s,n) for(int i=s;i<n;i++)
#define all(a) a.begin(),a.end()
#define rall(a) a.rbegin(),a.rend()
#define fs first
#define sc second
#define pb push_back
#define eb emplace_back
#define mp make_pair
#define INF 1e9
#define EPS 1e-9

using vd=vector<double>;
using vvd=vector<vd>;


int main(){
    int h,w;
    cin>>h>>w;
    vvi f(h+2,vi(w+2,1));
    vvi walk(h+2,vi(w+2,0));
    int gy,gx,y=0,x=0,v=0;
    range(i,1,h+1)range(j,1,w+1){
        char c;
        cin>>c;
        switch(c){
            case 'G': gy=i,gx=j,f[i][j]=0; break;
            case '.': f[i][j]=0;break;
            case '#': break;
            case '^': y=i,x=j,v=0,f[i][j]=0; break;
            case '>': y=i,x=j,v=1,f[i][j]=0; break;
            case 'v': y=i,x=j,v=2,f[i][j]=0; break;
            case '<': y=i,x=j,v=3,f[i][j]=0; break;
        }
    }
    walk[y][x]=1;
    rep(loop,1000000){
        vvi vec={{-1,0},{0,1},{1,0},{0,-1}};
        if(f[y+vec[(v+1)%4][0]][x+vec[(v+1)%4][1]]==0){ //右手が道なら右に曲がって前に進む
            //cout<<"hoge";
            v=(v+1)%4;
            y+=vec[v][0], x+=vec[v][1];
            walk[y][x]=1;
        }else if(f[y+vec[v][0]][x+vec[v][1]]==1){ //（右が壁で、）正面が壁なら左に回る
            //cout<<"fuga";
            v=(v+3)%4;
        }else{ //そうでないならまえに進む
            //cout<<"zako";
            y+=vec[v][0],x+=vec[v][1];
            walk[y][x]=1;
        }
        if(y==gy&&x==gx){
            break;
        }
        // cout<<y<<","<<x<<","<<v<<endl;
        // rep(i,h+2){
        //     rep(j,w+2){
        //         if(i==y&&j==x){
        //             cout<<"^>v<"[v];
        //         }else{
        //             cout<<".#"[f[i][j]];
        //         }
        //     }
        //     cout<<endl;
        // }
    }
    if(y==gy&&x==gx){
        int ans=0;
        rep(i,h+2)rep(j,w+2)ans+=walk[i][j];
        cout<<ans<<endl;
    }else cout<<-1<<endl;
	return 0;
}
accuracy: 1
time_ms: 210
memory_kb: 3192
final_rank: 7

code_snippet: #include <stdio.h>
#include <cmath>
#include <algorithm>
#include <cfloat>
#include <stack>
#include <queue>
#include <vector>
typedef long long int ll;
typedef unsigned long long int ull;
#define BIG_NUM 2000000000
#define MOD 1000000007
#define EPS 0.000000001
using namespace std;

enum DIR{
	North,
	East,
	South,
	West,
};

enum MIGITE{
	Mae,
	Migi_Mae,
	Migi,
	Migi_Ushiro,
};

int H,W,min_Time[50][50][4][4];
char map[50][51];

struct Info{
	Info(){
		row = col = count = 0;
		dir = North;
		migite_loc = Mae;
		migite_row = migite_col = 0;
		visit_count = 0;
	}

	Info(int arg_row,int arg_col,DIR arg_dir,MIGITE arg_migite_loc,int arg_count,int arg_migite_row,int arg_migite_col,int arg_visit_count){
		row = arg_row;
		col = arg_col;
		dir = arg_dir;
		migite_loc = arg_migite_loc;
		count = arg_count;
		migite_row = arg_migite_row;
		migite_col = arg_migite_col;
		visit_count = arg_visit_count;
	}
	void copy(bool arg_visited[50][50]){
		for(int a = 0; a < H; a++){
			for(int b = 0; b < W; b++){
				visited[a][b] = arg_visited[a][b];
			}
		}
	}

	int row,col,count,migite_row,migite_col,visit_count;
	DIR dir;
	MIGITE migite_loc;
	bool visited[50][50];
};

int diff_row_migite_N[4] = {-1,-1,0,1},diff_col_migite_N[4] = {0,1,1,1};
int diff_row_migite_E[4] = {0,1,1,1},diff_col_migite_E[4] = {1,1,0,-1};
int diff_row_migite_S[4] = {1,1,0,-1},diff_col_migite_S[4] = {0,-1,-1,-1};
int diff_row_migite_W[4] = {0,-1,-1,-1},diff_col_migite_W[4] = {-1,-1,0,1};
int diff_row_wall[8] = {-1,-1,-1,0,0,1,1,1},diff_col_wall[8] = {-1,0,1,-1,1,-1,0,1};



struct Data{
	int row,col;
};

bool rangeCheck(int row,int col){
	if(row >= 0 && row <= H-1 && col >= 0 && col <= W-1)return true;
	else{
		return false;
	}
}

DIR turn_right(DIR dir){
	switch(dir){
	case North:
		return East;
	case East:
		return South;
	case South:
		return West;
	case West:
		return North;
	}
	return North; //must not reach here
}

DIR turn_left(DIR dir){
	switch(dir){
	case North:
		return West;
	case East:
		return North;
	case South:
		return East;
	case West:
		return South;
	}
	return North; //must not reach here
}

bool isMigiteLeave(DIR next_dir,int next_row,int next_col,int migite_row,int migite_col){

	int tmp_diff_row[4],tmp_diff_col[4];

	switch(next_dir){
	case North:
		for(int i = 0; i < 4; i++){
			tmp_diff_row[i] = diff_row_migite_N[i];
			tmp_diff_col[i] = diff_col_migite_N[i];
		}
		break;
	case East:
		for(int i = 0; i < 4; i++){
			tmp_diff_row[i] = diff_row_migite_E[i];
			tmp_diff_col[i] = diff_col_migite_E[i];
		}
		break;
	case South:
		for(int i = 0; i < 4; i++){
			tmp_diff_row[i] = diff_row_migite_S[i];
			tmp_diff_col[i] = diff_col_migite_S[i];
		}
		break;
	case West:
		for(int i = 0; i < 4; i++){
			tmp_diff_row[i] = diff_row_migite_W[i];
			tmp_diff_col[i] = diff_col_migite_W[i];
		}
		break;
	}

	for(int i = 0; i < 4; i++){
		if(migite_row == next_row + tmp_diff_row[i] && migite_col == next_col + tmp_diff_col[i]){ //next_row,next_col?????????????±???????????????????????????????
			return false;
		}
	}

	return true;
}


MIGITE findMigitePos(DIR dir,int row,int col,int migite_row,int migite_col){

	int tmp_diff_row[4],tmp_diff_col[4];

	switch(dir){
	case North:
		for(int i = 0; i < 4; i++){
			tmp_diff_row[i] = diff_row_migite_N[i];
			tmp_diff_col[i] = diff_col_migite_N[i];
		}
		break;
	case East:
		for(int i = 0; i < 4; i++){
			tmp_diff_row[i] = diff_row_migite_E[i];
			tmp_diff_col[i] = diff_col_migite_E[i];
		}
		break;
	case South:
		for(int i = 0; i < 4; i++){
			tmp_diff_row[i] = diff_row_migite_S[i];
			tmp_diff_col[i] = diff_col_migite_S[i];
		}
		break;
	case West:
		for(int i = 0; i < 4; i++){
			tmp_diff_row[i] = diff_row_migite_W[i];
			tmp_diff_col[i] = diff_col_migite_W[i];
		}
		break;
	}

	for(int i = 0; i < 4; i++){
		if(migite_row == row + tmp_diff_row[i] && migite_col == col + tmp_diff_col[i]){
			switch(i){
			case 0:return Mae;
			case 1:return Migi_Mae;
			case 2:return Migi;
			case 3:return Migi_Ushiro;
			}
		}
	}
	return Mae; //Must not reach here
}

void func(){

	Info first;
	first.count = 0;

	for(int i = 0; i < H; i++){
		for(int k = 0; k < W; k++)first.visited[i][k] = false;
	}

	for(int row = 0; row < H; row++){
		for(int col = 0; col < W; col++){
			for(int a = 0; a < 4; a++){
				for(int b = 0; b < 4; b++)min_Time[row][col][a][b] = BIG_NUM;
			}
		}
	}


	for(int i = 0; i < H; i++){
		scanf("%s",map[i]);
		for(int k = 0; k < W; k++){
			switch(map[i][k]){
			case '^':
				first.row = i;
				first.col = k;
				first.migite_loc = Migi;
				first.dir = North;
				first.migite_row = i;
				first.migite_col = k+1;
				break;
			case 'v':
				first.row = i;
				first.col = k;
				first.migite_loc = Migi;
				first.dir = South;
				first.migite_row = i;
				first.migite_col = k-1;
				break;
			case '<':
				first.row = i;
				first.col = k;
				first.migite_loc = Migi;
				first.dir = West;
				first.migite_row = i-1;
				first.migite_col = k;
				break;
			case '>':
				first.row = i;
				first.col = k;
				first.migite_loc = Migi;
				first.dir = East;
				first.migite_row = i+1;
				first.migite_col = k;
				break;
			}
		}
	}

	min_Time[first.row][first.col][first.dir][first.migite_loc] = 0;
	first.visited[first.row][first.col] = true;
	first.visit_count++;

	int next_row,next_col,tmp_row,tmp_col;
	DIR next_dir;
	MIGITE tmp_migite_loc;

	int tmp_diff_row[4],tmp_diff_col[4];

	queue<Info> Q;
	int ans = BIG_NUM;

	Q.push(first);

	while(!Q.empty()){

		if(map[Q.front().row][Q.front().col] == 'G'){
			ans = min(ans,Q.front().visit_count);
			Q.pop();
		}else if(Q.front().count > min_Time[Q.front().row][Q.front().col][Q.front().dir][Q.front().migite_loc]){
			Q.pop();
		}else{

			switch(Q.front().dir){
			case North:
				next_row = Q.front().row-1;
				next_col = Q.front().col;
				break;
			case East:
				next_row = Q.front().row;
				next_col = Q.front().col+1;
				break;
			case South:
				next_row = Q.front().row+1;
				next_col = Q.front().col;
				break;
			case West:
				next_row = Q.front().row;
				next_col = Q.front().col-1;
				break;
			}

			next_dir = turn_right(Q.front().dir);

			if(isMigiteLeave(next_dir,Q.front().row,Q.front().col,Q.front().migite_row,Q.front().migite_col) == false){

				Info new_info;
				new_info.migite_loc = findMigitePos(next_dir,Q.front().row,Q.front().col,Q.front().migite_row,Q.front().migite_col);
				new_info.row = Q.front().row;
				new_info.col = Q.front().col;
				new_info.count = Q.front().count;
				new_info.dir = next_dir;
				new_info.migite_row = Q.front().migite_row;
				new_info.migite_col = Q.front().migite_col;
				new_info.copy(Q.front().visited);
				new_info.visit_count = Q.front().visit_count;
				if(min_Time[new_info.row][new_info.col][new_info.dir][new_info.migite_loc] > new_info.count){
					min_Time[new_info.row][new_info.col][new_info.dir][new_info.migite_loc] = new_info.count;
					Q.push(new_info);
				}
			}else{

				switch(Q.front().dir){
				case North:
					for(int i = 0; i < 4; i++){
						tmp_diff_row[i] = diff_row_migite_N[i];
						tmp_diff_col[i] = diff_col_migite_N[i];
					}
					break;
				case East:
					for(int i = 0; i < 4; i++){
						tmp_diff_row[i] = diff_row_migite_E[i];
						tmp_diff_col[i] = diff_col_migite_E[i];
					}
					break;
				case South:
					for(int i = 0; i < 4; i++){
						tmp_diff_row[i] = diff_row_migite_S[i];
						tmp_diff_col[i] = diff_col_migite_S[i];
					}
					break;
				case West:
					for(int i = 0; i < 4; i++){
						tmp_diff_row[i] = diff_row_migite_W[i];
						tmp_diff_col[i] = diff_col_migite_W[i];
					}
					break;
				}

				for(int i = 0; i < 4; i++){
					tmp_row = Q.front().row + tmp_diff_row[i];
					tmp_col = Q.front().col + tmp_diff_col[i];

					if(rangeCheck(tmp_row,tmp_col) == false || map[tmp_row][tmp_col] == '#'){
						for(int k = 0; k < 8; k++){
							if(Q.front().migite_row+diff_row_wall[k] == tmp_row && Q.front().migite_col+diff_col_wall[k] == tmp_col){

								tmp_migite_loc = findMigitePos(Q.front().dir,Q.front().row,Q.front().col,tmp_row,tmp_col);
								if(min_Time[Q.front().row][Q.front().col][Q.front().dir][tmp_migite_loc] > Q.front().count){
									min_Time[Q.front().row][Q.front().col][Q.front().dir][tmp_migite_loc] = Q.front().count;

									Info new_info;
									new_info.migite_loc = tmp_migite_loc;
									new_info.row = Q.front().row;
									new_info.col = Q.front().col;
									new_info.count = Q.front().count;
									new_info.dir = next_dir;
									new_info.migite_row = tmp_row;
									new_info.migite_col = tmp_col;
									new_info.copy(Q.front().visited);
									new_info.visit_count = Q.front().visit_count;

									Q.push(new_info);
								}
								break;
							}
						}
					}
				}

			}

			next_dir = turn_left(Q.front().dir);

			if(isMigiteLeave(next_dir,Q.front().row,Q.front().col,Q.front().migite_row,Q.front().migite_col) == false){

				Info new_info;
				new_info.migite_loc = findMigitePos(next_dir,Q.front().row,Q.front().col,Q.front().migite_row,Q.front().migite_col);
				new_info.row = Q.front().row;
				new_info.col = Q.front().col;
				new_info.count = Q.front().count;
				new_info.dir = next_dir;
				new_info.migite_row = Q.front().migite_row;
				new_info.migite_col = Q.front().migite_col;
				new_info.copy(Q.front().visited);
				new_info.visit_count = Q.front().visit_count;
				if(min_Time[new_info.row][new_info.col][new_info.dir][new_info.migite_loc] > new_info.count){
					min_Time[new_info.row][new_info.col][new_info.dir][new_info.migite_loc] = new_info.count;
					Q.push(new_info);
				}
			}else{

				switch(Q.front().dir){
				case North:
					for(int i = 0; i < 4; i++){
						tmp_diff_row[i] = diff_row_migite_N[i];
						tmp_diff_col[i] = diff_col_migite_N[i];
					}
					break;
				case East:
					for(int i = 0; i < 4; i++){
						tmp_diff_row[i] = diff_row_migite_E[i];
						tmp_diff_col[i] = diff_col_migite_E[i];
					}
					break;
				case South:
					for(int i = 0; i < 4; i++){
						tmp_diff_row[i] = diff_row_migite_S[i];
						tmp_diff_col[i] = diff_col_migite_S[i];
					}
					break;
				case West:
					for(int i = 0; i < 4; i++){
						tmp_diff_row[i] = diff_row_migite_W[i];
						tmp_diff_col[i] = diff_col_migite_W[i];
					}
					break;
				}

				for(int i = 0; i < 4; i++){
					tmp_row = Q.front().row + tmp_diff_row[i];
					tmp_col = Q.front().col + tmp_diff_col[i];

					if(rangeCheck(tmp_row,tmp_col) == false || map[tmp_row][tmp_col] == '#'){
						for(int k = 0; k < 8; k++){
							if(Q.front().migite_row+diff_row_wall[k] == tmp_row && Q.front().migite_col+diff_col_wall[k] == tmp_col){

								tmp_migite_loc = findMigitePos(Q.front().dir,Q.front().row,Q.front().col,tmp_row,tmp_col);
								if(min_Time[Q.front().row][Q.front().col][Q.front().dir][tmp_migite_loc] > Q.front().count){
									min_Time[Q.front().row][Q.front().col][Q.front().dir][tmp_migite_loc] = Q.front().count;
									Info new_info;
									new_info.migite_loc = tmp_migite_loc;
									new_info.row = Q.front().row;
									new_info.col = Q.front().col;
									new_info.count = Q.front().count;
									new_info.dir = Q.front().dir;
									new_info.migite_row = tmp_row;
									new_info.migite_col = tmp_col;
									new_info.copy(Q.front().visited);
									new_info.visit_count = Q.front().visit_count;

									Q.push(new_info);
								}
								break;
							}
						}
					}
				}

			}


			if(rangeCheck(next_row,next_col) == false || map[next_row][next_col] == '#'){
				//Do nothing
			}else{

				next_dir = Q.front().dir;

				if(isMigiteLeave(next_dir,next_row,next_col,Q.front().migite_row,Q.front().migite_col) == false){

					Info new_info;
					new_info.migite_loc = findMigitePos(next_dir,next_row,next_col,Q.front().migite_row,Q.front().migite_col);
					new_info.row = next_row;
					new_info.col = next_col;
					new_info.count = Q.front().count+1;
					new_info.dir = next_dir;
					new_info.migite_row = Q.front().migite_row;
					new_info.migite_col = Q.front().migite_col;
					new_info.copy(Q.front().visited);
					if(new_info.visited[next_row][next_col]){
						new_info.visit_count = Q.front().visit_count;
					}else{
						new_info.visited[next_row][next_col] = true;
						new_info.visit_count = Q.front().visit_count+1;
					}

					if(min_Time[new_info.row][new_info.col][new_info.dir][new_info.migite_loc] > new_info.count){
						min_Time[new_info.row][new_info.col][new_info.dir][new_info.migite_loc] = new_info.count;
						Q.push(new_info);
					}
				}else{

					switch(Q.front().dir){
					case North:
						for(int i = 0; i < 4; i++){
							tmp_diff_row[i] = diff_row_migite_N[i];
							tmp_diff_col[i] = diff_col_migite_N[i];
						}
						break;
					case East:
						for(int i = 0; i < 4; i++){
							tmp_diff_row[i] = diff_row_migite_E[i];
							tmp_diff_col[i] = diff_col_migite_E[i];
						}
						break;
					case South:
						for(int i = 0; i < 4; i++){
							tmp_diff_row[i] = diff_row_migite_S[i];
							tmp_diff_col[i] = diff_col_migite_S[i];
						}
						break;
					case West:
						for(int i = 0; i < 4; i++){
							tmp_diff_row[i] = diff_row_migite_W[i];
							tmp_diff_col[i] = diff_col_migite_W[i];
						}
						break;
					}

					for(int i = 0; i < 4; i++){
						tmp_row = Q.front().row + tmp_diff_row[i];
						tmp_col = Q.front().col + tmp_diff_col[i];

						if(rangeCheck(tmp_row,tmp_col) == false || map[tmp_row][tmp_col] == '#'){
							for(int k = 0; k < 8; k++){
								if(Q.front().migite_row+diff_row_wall[k] == tmp_row && Q.front().migite_col+diff_col_wall[k] == tmp_col){
									//??????????°?????????????
									tmp_migite_loc = findMigitePos(Q.front().dir,Q.front().row,Q.front().col,tmp_row,tmp_col);
									if(min_Time[Q.front().row][Q.front().col][next_dir][tmp_migite_loc] > Q.front().count){
										min_Time[Q.front().row][Q.front().col][next_dir][tmp_migite_loc] = Q.front().count;

										Info new_info;
										new_info.migite_loc = tmp_migite_loc;
										new_info.row = Q.front().row;
										new_info.col = Q.front().col;
										new_info.count = Q.front().count;
										new_info.dir = Q.front().dir;
										new_info.migite_row = tmp_row;
										new_info.migite_col = tmp_col;
										new_info.copy(Q.front().visited);
										new_info.visit_count = Q.front().visit_count;

										Q.push(new_info);
									}
									break;
								}
							}
						}
					}

				}
			}
			Q.pop();
		}
	}

	if(ans != BIG_NUM){
		printf("%d\n",ans);
	}else{
		printf("-1\n");
	}

}

int main(){

	scanf("%d %d",&H,&W);
	func();

	return 0;
}
accuracy: 1
time_ms: 30
memory_kb: 3000
final_rank: 1

code_snippet: #include <iostream>
#include <queue>
#include <cmath>
#define REP(i, a, n) for(int i = ((int) a); i < ((int) n); i++)
using namespace std;

struct state {
  int y, x, d, hy, hx, n;
  bool operator<(const state &s) const {
    return n > s.n;
  }
};

int N, M, D, SY, SX, GY, GX;
char S[52][52];
int dd[5] = { 0, 1, 0, -1, 0 };
bool visited[52][52][52][52][4];
bool step[52][52];

bool isin(int y, int x) {
  return 0 <= y && y < N + 2 && 0 <= x && x < M + 2;
}

bool ok(int y, int x, int d, int hy, int hx) {
  if(S[y][x] == '#') return false;
  if(S[hy][hx] != '#') return false;
  bool f = false;
  if(y + dd[d] == hy && x + dd[d + 1] == hx) f = true;
  if(y + dd[d] + dd[(d + 1) % 4] == hy && x + dd[d + 1] + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] == hy && x + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] + dd[(d + 2) % 4] == hy && x + dd[(d + 1) % 4 + 1] + dd[(d + 2) % 4 + 1] == hx) f = true;
  return f;
}

int main(void) {
  cin >> N >> M;
  REP(i, 0, N + 2) REP(j, 0, M + 2) S[i][j] = '#';
  REP(i, 1, N + 1) REP(j, 1, M + 1) {
    cin >> S[i][j];
    if(S[i][j] == '>') SY = i, SX = j, D = 0;
    if(S[i][j] == 'v') SY = i, SX = j, D = 1;
    if(S[i][j] == '<') SY = i, SX = j, D = 2;
    if(S[i][j] == '^') SY = i, SX = j, D = 3;
    if(S[i][j] == 'G') GY = i, GX = j;
  }

  REP(i, 0, 52) REP(j, 0, 52) REP(k, 0, 52) REP(l, 0, 52) REP(m, 0, 4) visited[i][j][k][l][m] = false;
  REP(i, 0, 52) REP(j, 0, 52) step[i][j] = false;
  priority_queue<state> q;
  q.push((state) { SY, SX, D, SY + dd[(D + 1) % 4], SX + dd[(D + 1) % 4 + 1], 1 });

  int ans = -1;
  while(q.size()) {
    state s = q.top();
    q.pop();

    if(visited[s.y][s.x][s.hy][s.hx][s.d]) continue;
    visited[s.y][s.x][s.hy][s.hx][s.d] = true;
    step[s.y][s.x] = true;

    if(s.y == GY && s.x == GX) {
      ans = s.n;
      break;
    }

    REP(i, -1, 2) {
      int nd = (s.d + i + 4) % 4;
      int ny = s.y + (i == 0 ? dd[nd] : 0);
      int nx = s.x + (i == 0 ? dd[nd + 1] : 0);
      int nhy = s.hy;
      int nhx = s.hx;
      int nn = s.n + (i == 0 && !step[ny][nx] ? 1 : 0);
      if(ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }

    REP(i, -1, 2) REP(j, -1, 2) {
      if(i == 0 && j == 0) continue;
      int nd = s.d;
      int ny = s.y;
      int nx = s.x;
      int nhy = s.hy + i;
      int nhx = s.hx + j;
      int nn = s.n;
      if(isin(nhy, nhx) && ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }
  }
  cout << ans << endl;

  return 0;
}
accuracy: 1
time_ms: 20
memory_kb: 31704
final_rank: 11

code_snippet: #include <iostream>
#include <queue>
#include <cmath>
#define REP(i, a, n) for(int i = ((int) a); i < ((int) n); i++)
using namespace std;

struct state {
  int y, x, d, hy, hx, n;
  bool operator<(const state &s) const {
    return n > s.n;
  }
};

int N, M, D, SY, SX, GY, GX;
char S[52][52];
int dd[5] = { 0, 1, 0, -1, 0 };
bool visited[52][52][52][52][4];
bool step[52][52];

bool isin(int y, int x) {
  return 0 <= y && y < N + 2 && 0 <= x && x < M + 2;
}

bool ok(int y, int x, int d, int hy, int hx) {
  if(S[y][x] == '#') return false;
  if(S[hy][hx] != '#') return false;
  bool f = false;
  if(y + dd[d] == hy && x + dd[d + 1] == hx) f = true;
  if(y + dd[d] + dd[(d + 1) % 4] == hy && x + dd[d + 1] + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] == hy && x + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] + dd[(d + 2) % 4] == hy && x + dd[(d + 1) % 4 + 1] + dd[(d + 2) % 4 + 1] == hx) f = true;
  return f;
}

int main(void) {
  cin >> N >> M;
  REP(i, 0, N + 2) REP(j, 0, N + 2) S[i][j] = '#';
  REP(i, 1, N + 1) REP(j, 1, M + 1) {
    cin >> S[i][j];
    if(S[i][j] == '>') SY = i, SX = j, D = 0;
    if(S[i][j] == 'v') SY = i, SX = j, D = 1;
    if(S[i][j] == '<') SY = i, SX = j, D = 2;
    if(S[i][j] == '^') SY = i, SX = j, D = 3;
    if(S[i][j] == 'G') GY = i, GX = j;
  }

  REP(i, 0, 52) REP(j, 0, 52) REP(k, 0, 52) REP(l, 0, 52) REP(m, 0, 4) visited[i][j][k][l][m] = false;
  REP(i, 0, 52) REP(j, 0, 52) step[i][j] = false;
  priority_queue<state> q;
  q.push((state) { SY, SX, D, SY + dd[(D + 1) % 4], SX + dd[(D + 1) % 4 + 1], 1 });

  int ans = -1;
  while(q.size()) {
    state s = q.top();
    q.pop();

    if(visited[s.y][s.x][s.hy][s.hx][s.d]) continue;
    visited[s.y][s.x][s.hy][s.hx][s.d] = true;
    step[s.y][s.x] = true;

    if(s.y == GY && s.x == GX) {
      ans = s.n;
      break;
    }

    REP(i, -1, 2) {
      int nd = (s.d + i + 4) % 4;
      int ny = s.y + (i == 0 ? dd[nd] : 0);
      int nx = s.x + (i == 0 ? dd[nd + 1] : 0);
      int nhy = s.hy;
      int nhx = s.hx;
      int nn = s.n + (i == 0 && !step[ny][nx] ? 1 : 0);
      if(ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }

    REP(i, -1, 2) REP(j, -1, 2) {
      if(i == 0 && j == 0) continue;
      int nd = s.d;
      int ny = s.y;
      int nx = s.x;
      int nhy = s.hy + i;
      int nhx = s.hx + j;
      int nn = s.n;
      if(isin(nhy, nhx) && ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }
  }
  cout << ans << endl;

  return 0;
}
accuracy: 0.3
time_ms: 20
memory_kb: 31696
final_rank: 16

code_snippet: #include <iostream>
#include <queue>
#include <cmath>
#define REP(i, a, n) for(int i = ((int) a); i < ((int) n); i++)
using namespace std;

struct state {
  int y, x, d, hy, hx, n;
  bool operator<(const state &s) const {
    return n > s.n;
  }
};

int N, M, D, SY, SX, GY, GX;
char S[52][52];
int dd[5] = { 0, 1, 0, -1, 0 };
bool visited[52][52][52][52][4];
bool step[52][52];

bool isin(int y, int x) {
  return 0 <= y && y < N + 2 && 0 <= x && x < M + 2;
}

bool ok(int y, int x, int d, int hy, int hx) {
  if(S[y][x] == '#') return false;
  if(S[hy][hx] != '#') return false;
  bool f = false;
  if(y + dd[d] == hy && x + dd[d + 1] == hx) f = true;
  if(y + dd[d] + dd[(d + 1) % 4] == hy && x + dd[d + 1] + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] == hy && x + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] + dd[(d + 2) % 4] == hy && x + dd[(d + 1) % 4 + 1] + dd[(d + 2) % 4 + 1] == hx) f = true;
  return f;
}

int main(void) {
  cin >> N >> M;
  REP(i, 0, N + 2) REP(j, 0, N + 2) S[i][j] = '#';
  REP(i, 1, N + 1) REP(j, 1, M + 1) {
    cin >> S[i][j];
    if(S[i][j] == '>') SY = i, SX = j, D = 0;
    if(S[i][j] == 'V') SY = i, SX = j, D = 1;
    if(S[i][j] == '<') SY = i, SX = j, D = 2;
    if(S[i][j] == '^') SY = i, SX = j, D = 3;
    if(S[i][j] == 'G') GY = i, GX = j;
  }

  REP(i, 0, 52) REP(j, 0, 52) REP(k, 0, 52) REP(l, 0, 52) REP(m, 0, 4) visited[i][j][k][l][m] = false;
  REP(i, 0, 52) REP(j, 0, 52) step[i][j] = false;
  priority_queue<state> q;
  q.push((state) { SY, SX, D, SY + dd[(D + 1) % 4], SX + dd[(D + 1) % 4 + 1], 1 });

  int ans = -1;
  while(q.size()) {
    state s = q.top();
    q.pop();

    if(visited[s.y][s.x][s.hy][s.hx][s.d]) continue;
    visited[s.y][s.x][s.hy][s.hx][s.d] = true;
    step[s.y][s.x] = true;

    if(s.y == GY && s.x == GX) {
      ans = s.n;
      break;
    }

    REP(i, -1, 2) {
      int nd = (s.d + i + 4) % 4;
      int ny = s.y + (i == 0 ? dd[nd] : 0);
      int nx = s.x + (i == 0 ? dd[nd + 1] : 0);
      int nhy = s.hy;
      int nhx = s.hx;
      int nn = s.n + (i == 0 && !step[ny][nx] ? 1 : 0);
      if(ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }

    REP(i, -1, 2) REP(j, -1, 2) {
      if(i == 0 && j == 0) continue;
      int nd = s.d;
      int ny = s.y;
      int nx = s.x;
      int nhy = s.hy + i;
      int nhx = s.hx + j;
      int nn = s.n;
      if(isin(nhy, nhx) && ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }
  }
  cout << ans << endl;

  return 0;
}
accuracy: 0.08333333333333333
time_ms: 10
memory_kb: 31656
final_rank: 18

code_snippet: #include <iostream>
#include <queue>
#include <cmath>
#define REP(i, a, n) for(int i = ((int) a); i < ((int) n); i++)
using namespace std;

struct state {
  int y, x, d, hy, hx, n;
  bool operator<(const state &s) const {
    return n > s.n;
  }
};

int N, M, D, SY, SX, GY, GX;
char S[52][52];
int dd[5] = { 0, 1, 0, -1, 0 };
bool visited[52][52][52][52][4];
bool step[52][52];

bool isin(int y, int x) {
  return 0 <= y && y < N + 2 && 0 <= x && x < M + 2;
}

bool ok(int y, int x, int d, int hy, int hx) {
  if(S[y][x] == '#') return false;
  if(S[hy][hx] != '#') return false;
  bool f = false;
  if(y + dd[d] == hy && x + dd[d + 1] == hx) f = true;
  if(y + dd[d] + dd[(d + 1) % 4] == hy && x + dd[d + 1] + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] == hy && x + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] + dd[(d + 2) % 4] == hy && x + dd[(d + 1) % 4 + 1] + dd[(d + 2) % 4 + 1] == hx) f = true;
  return f;
}

int main(void) {
  cin >> N >> M;
  REP(i, 0, N + 2) REP(j, 0, N + 2) S[i][j] = '#';
  REP(i, 1, N + 1) REP(j, 1, M + 1) {
    cin >> S[i][j];
    if(S[i][j] == '>') SY = i, SX = j, D = 0;
    if(S[i][j] == 'V') SY = i, SX = j, D = 1;
    if(S[i][j] == '<') SY = i, SX = j, D = 2;
    if(S[i][j] == '^') SY = i, SX = j, D = 3;
    if(S[i][j] == 'G') GY = i, GX = j;
  }

  REP(i, 0, 52) REP(j, 0, 52) REP(k, 0, 52) REP(l, 0, 52) REP(m, 0, 4) visited[i][j][k][l][m] = false;
  REP(i, 0, 52) REP(j, 0, 52) step[i][j] = false;
  priority_queue<state> q;
  q.push((state) { SY, SX, D, SY + dd[(D + 1) % 4], SX + dd[(D + 1) % 4 + 1], 1 });

  int ans = -1;
  while(q.size()) {
    state s = q.top();
    q.pop();

    if(visited[s.y][s.x][s.hy][s.hx][s.d]) continue;
    visited[s.y][s.x][s.hy][s.hx][s.d] = true;
    step[s.y][s.x] = true;

    if(s.y == GY && s.x == GX) {
      ans = s.n;
      break;
    }

    REP(i, -1, 2) {
      int nd = (s.d + i + 4) % 4;
      int ny = s.y + (i == 0 ? dd[nd] : 0);
      int nx = s.x + (i == 0 ? dd[nd + 1] : 0);
      int nhy = s.hy;
      int nhx = s.hx;
      bool f = true;
      int nn = s.n + (i == 0 && !step[ny][nx] ? 1 : 0);
      if(ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }

    REP(i, -1, 2) REP(j, -1, 2) {
      if(i == 0 && j == 0) continue;
      int nd = s.d;
      int ny = s.y;
      int nx = s.x;
      int nhy = s.hy + i;
      int nhx = s.hx + j;
      int nn = s.n;
      if(isin(nhy, nhx) && ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }
  }
  cout << ans << endl;

  return 0;
}
accuracy: 0.08333333333333333
time_ms: 10
memory_kb: 31656
final_rank: 18

code_snippet: #include <iostream>
#include <queue>
#include <cmath>
#define REP(i, a, n) for(int i = ((int) a); i < ((int) n); i++)
using namespace std;

struct state {
  int y, x, d, hy, hx, n;
  bool operator<(const state &s) const {
    return n > s.n;
  }
};

int N, M, D, SY, SX, GY, GX;
char S[52][52];
int dd[5] = { 0, 1, 0, -1, 0 };
bool visited[52][52][52][52][4];
bool step[52][52];

bool isin(int y, int x) {
  return 0 <= y && y < N + 2 && 0 <= x && x < M + 2;
}

bool ok(int y, int x, int d, int hy, int hx) {
  if(S[y][x] == '#') return false;
  if(S[hy][hx] != '#') return false;
  bool f = false;
  if(y + dd[d] == hy && x + dd[d + 1] == hx) f = true;
  if(y + dd[d] + dd[(d + 1) % 4] == hy && x + dd[d + 1] + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] == hy && x + dd[(d + 1) % 4 + 1] == hx) f = true;
  if(y + dd[(d + 1) % 4] + dd[(d + 2) % 4] == hy && x + dd[(d + 1) % 4 + 1] + dd[(d + 2) % 4 + 1] == hx) f = true;
  return f;
}

int main(void) {
  cin >> N >> M;
  REP(i, 0, N + 2) REP(j, 0, N + 2) S[i][j] = '#';
  REP(i, 1, N + 1) REP(j, 1, M + 1) {
    cin >> S[i][j];
    if(S[i][j] == '>') SY = i, SX = j, D = 0;
    if(S[i][j] == 'V') SY = i, SX = j, D = 1;
    if(S[i][j] == '<') SY = i, SX = j, D = 2;
    if(S[i][j] == '^') SY = i, SX = j, D = 3;
    if(S[i][j] == 'G') GY = i, GX = j;
  }

  REP(i, 0, 52) REP(j, 0, 52) REP(k, 0, 52) REP(l, 0, 52) REP(m, 0, 4) visited[i][j][k][l][m] = false;
  priority_queue<state> q;
  q.push((state) { SY, SX, D, SY + dd[(D + 1) % 4], SX + dd[(D + 1) % 4 + 1], 1 });

  int ans = -1;
  while(q.size()) {
    state s = q.top();
    q.pop();

    if(visited[s.y][s.x][s.hy][s.hx][s.d]) continue;
    visited[s.y][s.x][s.hy][s.hx][s.d] = true;
    step[s.y][s.x] = true;

    if(s.y == GY && s.x == GX) {
      ans = s.n;
      break;
    }

    REP(i, -1, 2) {
      int nd = (s.d + i + 4) % 4;
      int ny = s.y + (i == 0 ? dd[nd] : 0);
      int nx = s.x + (i == 0 ? dd[nd + 1] : 0);
      int nhy = s.hy;
      int nhx = s.hx;
      bool f = true;
      int nn = s.n + (i == 0 && !step[ny][nx] ? 1 : 0);
      if(ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }

    REP(i, -1, 2) REP(j, -1, 2) {
      if(i == 0 && j == 0) continue;
      int nd = s.d;
      int ny = s.y;
      int nx = s.x;
      int nhy = s.hy + i;
      int nhx = s.hx + j;
      int nn = s.n;
      if(isin(nhy, nhx) && ok(ny, nx, nd, nhy, nhx)) {
        q.push((state) { ny, nx, nd, nhy, nhx, nn });
      }
    }
  }
  cout << ans << endl;

  return 0;
}
accuracy: 0.08333333333333333
time_ms: 10
memory_kb: 31656
final_rank: 18

code_snippet: #include <iostream>
#include <vector>
#include <queue>
#include <tuple>
#include <cmath>
#include <set>
using namespace std;

constexpr int INF = 1e9;

using P = pair<int, int>;
using data = tuple<int, int, int, int, set<P>>; // dir, right hand, y, x
// right hand: 0 -> front, 1 -> right front, 2 -> right, 3 -> back right

int main() {
    int N, M;
    cin >> N >> M;
    vector<string> v(N);
    vector<vector<vector<vector<int>>>> res(4, vector<vector<vector<int>>>(4, vector<vector<int>>(N, vector<int>(M, INF))));
    queue<data> que;
    for(int i=0; i<N; ++i) {
        cin >> v[i];
    }
    int gy = 0, gx = 0;
    for(int i=0; i<N; ++i) {
        for(int j=0; j<M; ++j) {
            set<P> s;
            if(v[i][j] == '^') {
                res[0][2][i][j] = 0;
                s.insert(P{i, j});
                que.push(make_tuple(0, 2, i, j, s));
            } else if(v[i][j] == '<') {
                res[1][2][i][j] = 0;
                s.insert(P{i, j});
                que.push(make_tuple(1, 2, i, j, s));
            } else if(v[i][j] == 'v') {
                res[2][2][i][j] = 0;
                s.insert(P{i, j});
                que.push(make_tuple(2, 2, i, j, s));
            } else if(v[i][j] == '>') {
                res[3][2][i][j] = 0;
                s.insert(P{i, j});
                que.push(make_tuple(3, 2, i, j, s));
            }
            if(v[i][j] == 'G') {
                gy = i; gx = j;
            }
        }
    }
    int dx[4] = {0, -1, 0, 1},
        dy[4] = {-1, 0, 1, 0};
    int hand_pos_x[4][4] = {{0, 1, 1, 1},
                            {-1, -1, 0, 1},
                            {0, -1, -1, -1},
                            {1, 1, 0, -1}};
    int hand_pos_y[4][4] = {{-1, -1, 0, 1},
                            {0, -1, -1, -1},
                            {1, 1, 0, -1},
                            {0, 1, 1, 1}};
    int ans = INF;
    while(!que.empty()) {
        int dir, hand, y, x;
        set<P> s;
        tie(dir, hand, y, x, s) = que.front(); que.pop();
        if(v[y][x] == 'G') {
            ans = min(ans, (int)s.size());
            continue;
        }
        int now = s.size();
        //cout << "d: " << dir << "  h: " << hand << "  y: " << y << "  x: " << x << "  t: " << now << endl;
        
        if(hand == 0 && res[(dir+1)%4][2][y][x] > now) {
            res[(dir+1)%4][2][y][x] = now;
            que.push(make_tuple((dir+1)%4, 2, y, x, s));
        } else if(hand == 1 && res[(dir+1)%4][3][y][x] > now) {
            res[(dir+1)%4][3][y][x] = now;
            que.push(make_tuple((dir+1)%4, 3, y, x, s));
        } else if(hand == 2 && res[(dir+3)%4][0][y][x] > now) {
            res[(dir+3)%4][0][y][x] = now;
            que.push(make_tuple((dir+3)%4, 0, y, x, s));
        } else if(hand == 3 && res[(dir+3)%4][1][y][x] > now) {
            res[(dir+3)%4][1][y][x] = now;
            que.push(make_tuple((dir+3)%4, 1, y, x, s));
        }

        for(int i=hand+1; i<4; ++i) {
            int hand_nx = x + hand_pos_x[dir][i],
                hand_ny = y + hand_pos_y[dir][i];
            if(hand_nx < 0 || M <= hand_nx || hand_ny < 0 || N <= hand_ny || v[hand_ny][hand_nx] == '#') {
                if(res[dir][i][y][x] > now) {
                    res[dir][i][y][x] = now;
                    que.push(make_tuple(dir, i, y, x, s));
                }
            } else if(i != 1) {
                break;
            }
        }
        for(int i=hand-1; i>=0; --i) {
            int hand_nx = x + hand_pos_x[dir][i],
                hand_ny = y + hand_pos_y[dir][i];
            if(hand_nx < 0 || M <= hand_nx || hand_ny < 0 || N <= hand_ny || v[hand_ny][hand_nx] == '#') {
                if(res[dir][i][y][x] > now) {
                    res[dir][i][y][x] = now;
                    que.push(make_tuple(dir, i, y, x, s));
                }
            } else if(i != 1){
                break;
            }
        }
        int ny = y + dy[dir], nx = x + dx[dir];
        if(0 <= ny && ny < N && 0 <= nx && nx < M && v[ny][nx] != '#' && hand != 3 && res[dir][hand+1][ny][nx] > now+1) {
            s.insert(P{ny, nx});
            res[dir][hand+1][ny][nx] = s.size();
            que.push(make_tuple(dir, hand+1, ny, nx, move(s)));
        }
    }
    cout << (ans == INF ? -1 : ans) << endl;
}
accuracy: 1
time_ms: 680
memory_kb: 3756
final_rank: 9

code_snippet: //#include<bits/stdc++.h>
#include<iostream>
#include<vector>
#include<queue>
#include<set>
#include<cstring>
using namespace std;
typedef pair<int,int> XY;
struct P{
  int x,y,d;
  set<XY> s;
  P(){}
  P(int x,int y,int d,set<XY> s):x(x),y(y),d(d),s(s){}
};
 
string st[52];
int n,m;
 
int main(){
  cin >> n >> m;
  int i,j,k;
  for(j=0;j<m+2;j++){
    st[0]+="#";
    st[n+1]+="#";
  }
  P p,b;
  for(i=1;i<=n;i++){
    cin >> st[i];
    for(j=0;j<m;j++){
      if(st[i][j]=='^'){
	p.x=j+1;p.y=i;p.d=0;st[i][j]='.';
      }
      if(st[i][j]=='>'){
	p.x=j+1;p.y=i;p.d=1;st[i][j]='.';
      }
      if(st[i][j]=='v'){
	p.x=j+1;p.y=i;p.d=2;st[i][j]='.';
      }
      if(st[i][j]=='<'){
	p.x=j+1;p.y=i;p.d=3;st[i][j]='.';
      }
    }
    st[i]="#"+st[i]+"#";
  }
 
  //for(i=0;i<=n+1;i++) cout << st[i] << endl;
 
  int ax[]={0,1,0,-1};
  int ay[]={-1,0,1,0};
  
  int rx[]={1,0,-1,0};
  int ry[]={0,1,0,-1};
 
  bool f=false;
  int o;
  int inf = 1 << 20;
  bool used[55][55][4];
  memset(used,false,sizeof(used));
  queue<P> q;
  p.s.clear();
  q.push(p);
  while(!q.empty()){
    p=q.front();q.pop();    
    //cout << p.y <<":"<< p.x <<"/"<< p.d << ":"<<p.s.size()<<endl;
    //cout << used[p.y][p.x][p.d]<<":"<<p.s.size()<<endl;
    if(used[p.y][p.x][p.d]) continue;
    used[p.y][p.x][p.d]=true;

    p.s.insert(XY(p.x,p.y));
  
    if(st[p.y][p.x]=='G') {
      f=true;
      o=p.s.size();
      break;
    }
    
    if(st[p.y+ry[p.d]][p.x+rx[p.d]]!='#') q.push(P(p.x+rx[p.d],p.y+ry[p.d],(p.d+1)%4,p.s));
    else if(st[p.y+ay[p.d]][p.x+ax[p.d]]!='#') q.push(P(p.x+ax[p.d],p.y+ay[p.d],p.d,p.s));
    else q.push(P(p.x,p.y,(p.d+3)%4,p.s));
  }
  if(f){
    cout << o << endl;
  }
  else cout << -1 << endl;
  return 0;
}
accuracy: 1
time_ms: 330
memory_kb: 1496
final_rank: 8

code_snippet: #include <bits/stdc++.h>
using namespace std;

#define rep(i,a,b) for(int i=a;i<b;i++)

enum { UP = 0, UP_RIGHT, RIGHT, DOWN_RIGHT, DOWN, DOWN_LEFT, LEFT, UP_LEFT };
int dx[8] = { 0,1,1,1,0,-1,-1,-1 };
int dy[8] = { -1,-1,0,1,1,1,0,-1 };

#define INF INT_MAX/2
typedef tuple<int, int, int, int> Node;
typedef pair<Node, int> pii;
typedef tuple<Node, Node, int> pnni;

struct Comp {
	bool operator() (pnni a, pnni b) {
		int aa = get<2>(a);
		int bb = get<2>(b);
		return aa > bb;
	}
};

int main()
{
	int H, W;
	cin >> H >> W;

	vector< vector<char> > S(H+2, vector<char>(W+2, '#'));
	rep(y, 1, H + 1)
	{
		string s; cin >> s;
		rep(x, 1, W + 1) S[y][x] = s[x - 1];
	}

	map<Node, int> dist;
	map<Node, Node> done;
	priority_queue<pnni, vector<pnni>, Comp> que;

	rep(y, 0, H+2) rep(x, 0, W+2)
	{
		if (S[y][x] == '#') continue;
		if (S[y][x] == '.') continue;
		if (S[y][x] == 'G') continue;

		int d;
		switch (S[y][x])
		{
		case '^': d = 0; break;
		case '>': d = 2; break;
		case 'v': d = 4; break;
		case '<': d = 6; break;
		}

		rep(h, 0, 4)
		{
			int xx = x + dx[(d + h) % 8];
			int yy = y + dy[(d + h) % 8];
			if (S[yy][xx] == '#')
			{
				Node s = Node(x, y, d, h);
				dist[s] = 1;
				que.push(pnni(s, Node(-1, -1, -1, -1), 1));
			}
		}
	}

	while (!que.empty())
	{
		pnni p = que.top(); que.pop();
		Node to = get<0>(p);
		Node from = get<1>(p);
		int cost = get<2>(p);
		if (done.find(to) != done.end()) continue;
		done[to] = from;

		int x = get<0>(to);
		int y = get<1>(to);
		int d = get<2>(to);
		int h = get<3>(to);

		if (S[y][x] == 'G')
		{
			set<Node> ans;
			Node n = to;
			while (0 <= get<0>(n))
			{
				ans.insert(Node(get<0>(n), get<1>(n), 0, 0));
				n = done[n];
			}
			cout << ans.size() << endl;
			return 0;
		}

		// ??????
		while(1){
			if (h == 3) break;

			int xx = x + dx[d];
			int yy = y + dy[d];
			if (S[yy][xx] == '#') break;

			Node next(xx, yy, d, h + 1);

			if (dist.find(next) == dist.end()) dist[next] = INF;
			int newcost = cost + 1;
			if (newcost < dist[next])
			{
				dist[next] = newcost;
				que.push(pnni(next, to, newcost));
			}

			break;
		}

		// 90??????????????¢
		while (1)
		{
			if (h < 2) break;

			Node next(x, y, (d + 2) % 8, h - 2);

			if (dist.find(next) == dist.end()) dist[next] = INF;
			int newcost = cost;
			if (newcost < dist[next])
			{
				dist[next] = newcost;
				que.push(pnni(next, to, newcost));
			}

			break;
		}

		// 90??????????????¢
		while (1)
		{
			if (1 < h) break;

			Node next(x, y, (d + 6) % 8, h + 2);

			if (dist.find(next) == dist.end()) dist[next] = INF;
			int newcost = cost;
			if (newcost < dist[next])
			{
				dist[next] = newcost;
				que.push(pnni(next, to, newcost));
			}

			break;
		}

		// 0
		while (1)
		{
			if (h != 0) break;

			int xx = x + dx[(d + h + 2) % 8];
			int yy = y + dy[(d + h + 2) % 8];
			if (S[yy][xx] == '#')
			{
				Node next(x, y, d, (h + 2) % 8);

				if (dist.find(next) == dist.end()) dist[next] = INF;
				int newcost = cost;
				if (newcost < dist[next])
				{
					dist[next] = newcost;
					que.push(pnni(next, to, newcost));
				}
			}
			else
			{
				int xxx = x + dx[(d + h + 1) % 8];
				int yyy = y + dy[(d + h + 1) % 8];
				if (S[yyy][xxx] != '#') break;

				Node next(x, y, d, (h + 1) % 8);

				if (dist.find(next) == dist.end()) dist[next] = INF;
				int newcost = cost;
				if (newcost < dist[next])
				{
					dist[next] = newcost;
					que.push(pnni(next, to, newcost));
				}
			}

			break;
		}

		// 1
		while (1)
		{
			if (h != 1) break;

			int xx = x + dx[(d + h - 1 + 8) % 8];
			int yy = y + dy[(d + h - 1 + 8) % 8];
			if (S[yy][xx] == '#')
			{
				Node next(x, y, d, (h - 1 + 8) % 8);

				if (dist.find(next) == dist.end()) dist[next] = INF;
				int newcost = cost;
				if (newcost < dist[next])
				{
					dist[next] = newcost;
					que.push(pnni(next, to, newcost));
				}
			}
			
			xx = x + dx[(d + h + 1 + 8) % 8];
			yy = y + dy[(d + h + 1 + 8) % 8];
			if (S[yy][xx] == '#')
			{
				Node next(x, y, d, (h + 1 + 8) % 8);

				if (dist.find(next) == dist.end()) dist[next] = INF;
				int newcost = cost;
				if (newcost < dist[next])
				{
					dist[next] = newcost;
					que.push(pnni(next, to, newcost));
				}
			}

			break;
		}

		// 2
		while (1)
		{
			if (h != 2) break;

			int xx = x + dx[(d + h - 2 + 8) % 8];
			int yy = y + dy[(d + h - 2 + 8) % 8];
			if (S[yy][xx] == '#')
			{
				Node next(x, y, d, (h - 2 + 8) % 8);

				if (dist.find(next) == dist.end()) dist[next] = INF;
				int newcost = cost;
				if (newcost < dist[next])
				{
					dist[next] = newcost;
					que.push(pnni(next, to, newcost));
				}
			}
			else
			{
				xx = x + dx[(d + h - 1 + 8) % 8];
				yy = y + dy[(d + h - 1 + 8) % 8];
				if (S[yy][xx] == '#')
				{
					Node next(x, y, d, (h - 1 + 8) % 8);

					if (dist.find(next) == dist.end()) dist[next] = INF;
					int newcost = cost;
					if (newcost < dist[next])
					{
						dist[next] = newcost;
						que.push(pnni(next, to, newcost));
					}
				}
			}

			xx = x + dx[(d + h + 1 + 8) % 8];
			yy = y + dy[(d + h + 1 + 8) % 8];
			if (S[yy][xx] == '#')
			{
				Node next(x, y, d, (h + 1 + 8) % 8);

				if (dist.find(next) == dist.end()) dist[next] = INF;
				int newcost = cost;
				if (newcost < dist[next])
				{
					dist[next] = newcost;
					que.push(pnni(next, to, newcost));
				}
			}

			break;
		}


		// 3
		while (1)
		{
			if (h != 2) break;

			int xx = x + dx[(d + h + 1 + 8) % 8];
			int yy = y + dy[(d + h + 1 + 8) % 8];
			if (S[yy][xx] == '#')
			{
				Node next(x, y, d, (h + 1 + 8) % 8);

				if (dist.find(next) == dist.end()) dist[next] = INF;
				int newcost = cost;
				if (newcost < dist[next])
				{
					dist[next] = newcost;
					que.push(pnni(next, to, newcost));
				}
			}

			break;
		}
	}

	cout << -1 << endl;
}
accuracy: 1
time_ms: 10
memory_kb: 5400
final_rank: 6

code_snippet: #include <bits/stdc++.h>

using namespace std;

int Dx[4] = {0, 1, 0, -1};
int Dy[4] = {1, 0, -1, 0};

int dhx[4][4] = {
	{0, 1, 1, 1},
	{1, 1, 0, -1},
	{0, -1, -1, -1},
	{-1, -1, 0, 1},
};
int dhy[4][4] = {
	{1, 1, 0, -1},
	{0, -1, -1, -1},
	{-1, -1, 0, 1},
	{0, 1, 1, 1},
};

struct Node {
	int x, y, hx, hy, dir;
};

int H, W;
int wall[50][50] = {0};
bool used[50][50] = {0};
bool reach[50][50][51][51][4] = {0};
bool inRange(int x, int y) {
	return 0 <= x && x < W && 0 <= y && y < H;
}
bool inRange2(int x, int y) {
	return -1 <= x && x <= W && -1 <= y && y <= H;
}
bool Wall(int x, int y) {
	if (inRange(x, y)) return wall[y][x];
	return true;
}
bool isInvalidHand(int px, int py, int hx, int hy, int dir) {
//	cout << ":" << px << " " << py << " " << hx << " " << hy << endl;
	if (!Wall(hx, hy)) return true;
	for (int i = 0; i < 4; ++i) {
		int x = px + dhx[dir][i];
		int y = py + dhy[dir][i];
		if (inRange2(x, y) && hx == x && hy == y) {
			return false;
		}
	}
	return true;
}

int main() {
	cin >> H >> W;

	for (int i = 0; i < 4; ++i) {
		Dy[i] = -Dy[i];
		for (int j = 0; j < 4; ++j) {
			dhy[i][j] = -dhy[i][j];
		}
	}

	int sx = -1, sy = -1, sd = -1;
	int gx = -1, gy = -1;
	for (int y = 0; y < H; ++y) {
		string str; cin >> str;
		for (int x = 0; x < W; ++x) {
			switch (str[x]) {
			case '#': wall[y][x] = true; break;
			case 'G': gx = x, gy = y; break;
			case '^': sx = x, sy = y; sd = 0; break;
			case '>': sx = x, sy = y; sd = 1; break;
			case 'v': sx = x, sy = y; sd = 2; break;
			case '<': sx = x, sy = y; sd = 3; break;
			}
		}
	}
	int ans = -1;
	queue<Node> Q;
	fill(used[0], used[50], false);
	fill(reach[0][0][0][0], reach[49][49][50][51], false);
	Q.push((Node){sx, sy, sx + Dx[(sd+1)%4], sy + Dy[(sd+1)%4], sd});
	while ( !Q.empty() ) {
		Node node = Q.front(); Q.pop();
		int px = node.x, py = node.y, hx = node.hx, hy = node.hy, dir = node.dir;
		if ( !inRange(px, py) ) continue;
		if ( wall[py][px] ) continue;
		if ( !inRange2(hx, hy) ) continue;
		if ( reach[py][px][hy+1][hx+1][dir] ) continue;
		if ( isInvalidHand(px, py, hx, hy, dir) ) continue;
		reach[py][px][hy+1][hx+1][dir] = true;
		used[py][px] = true;
		if (px == gx && py == gy) {
			break;
		}
//			cout << px << " " << py << " " << hx << " " << hy << " " << dir << endl;

		// move player
		{
			int npx = px + Dx[dir];
			int npy = py + Dy[dir];
			Q.push((Node){npx, npy, hx, hy, dir});
		}

		// move hand
		for (int dx = -1; dx <= 1; ++dx) for (int dy = -1; dy <= 1; ++dy) {
			int nhx = hx + dx;
			int nhy = hy + dy;
			if ( inRange2(nhx, nhy) && Wall(hx, hy) ) {
				Q.push((Node){px, py, nhx, nhy, dir});
			}
		}

		// change dir / turn
		Q.push((Node){px, py, hx, hy, (dir+1)%4});
		Q.push((Node){px, py, hx, hy, (dir-1+4)%4});
	}
	int s = 0;
	for (int y = 0; y < H; ++y) {
		for (int x = 0; x < W; ++x) {
			s += used[y][x];
		}
	}
	if (used[gy][gx] && (ans < 0 || s < ans)) {
		ans = s;
	}
	cout << ans << endl;
}
accuracy: 0.8666666666666667
time_ms: 10
memory_kb: 26640
final_rank: 13

code_snippet: #include <bits/stdc++.h>

using namespace std;

int Dx[4] = {0, 1, 0, -1};
int Dy[4] = {1, 0, -1, 0};

int dhx[4][4] = {
	{0, 1, 1, 1},
	{1, 1, 0, -1},
	{0, -1, -1, -1},
	{-1, -1, 0, 1},
};
int dhy[4][4] = {
	{1, 1, 0, -1},
	{0, -1, -1, -1},
	{-1, -1, 0, 1},
	{0, 1, 1, 1},
};

struct Node {
	int x, y, hx, hy, dir;
};

int H, W;
int wall[50][50] = {0};
bool used[50][50] = {0};
bool reach[50][50][51][51][4] = {0};
bool inRange(int x, int y) {
	return 0 <= x && x < W && 0 <= y && y < H;
}
bool inRange2(int x, int y) {
	return -1 <= x && x <= W && -1 <= y && y <= H;
}
bool Wall(int x, int y) {
	if (inRange(x, y)) return wall[y][x];
	if (inRange2(x, y)) return true;
	return false;
}
bool isInvalidHand(int px, int py, int hx, int hy, int dir) {
//	cout << ":" << px << " " << py << " " << hx << " " << hy << endl;
	if (!Wall(hx, hy)) return true;
	for (int i = 0; i < 4; ++i) {
		int x = px + dhx[dir][i];
		int y = py + dhy[dir][i];
		if (inRange2(x, y) && hx == x && hy == y) {
			return false;
		}
	}
	return true;
}

int main() {
	cin >> H >> W;

	for (int i = 0; i < 4; ++i) {
		Dy[i] = -Dy[i];
		for (int j = 0; j < 4; ++j) {
			dhy[i][j] = -dhy[i][j];
		}
	}

	int sx = -1, sy = -1, sd = -1;
	int gx = -1, gy = -1;
	for (int y = 0; y < H; ++y) {
		string str; cin >> str;
		for (int x = 0; x < W; ++x) {
			switch (str[x]) {
			case '#': wall[y][x] = true; break;
			case 'G': gx = x, gy = y; break;
			case '^': sx = x, sy = y; sd = 0; break;
			case '>': sx = x, sy = y; sd = 1; break;
			case 'v': sx = x, sy = y; sd = 2; break;
			case '<': sx = x, sy = y; sd = 3; break;
			}
		}
	}
	int ans = -1;
	for (int i = 0; i < 4; ++i) {
		queue<Node> Q;
		fill(used[0], used[50], false);
		fill(reach[0][0][0][0], reach[49][49][50][51], false);
		{
			int x = sx + Dx[(sd+1)%4];
			int y = sy + Dy[(sd+1)%4];
			Q.push((Node){sx, sy, x, y, sd});
		}
		while ( !Q.empty() ) {
			Node node = Q.front(); Q.pop();
			int px = node.x, py = node.y, hx = node.hx, hy = node.hy, dir = node.dir;
			if ( !inRange(px, py) ) continue;
			if ( wall[py][px] ) continue;
			if ( !inRange2(hx, hy) ) continue;
			if ( reach[py][px][hy+1][hx+1][dir] ) continue;
			if ( isInvalidHand(px, py, hx, hy, dir) ) continue;
			reach[py][px][hy+1][hx+1][dir] = true;
			used[py][px] = true;
			if (px == gx && py == gy) {
				break;
			}
//			cout << px << " " << py << " " << hx << " " << hy << " " << dir << endl;

			// move player
			{
				int npx = px + Dx[dir];
				int npy = py + Dy[dir];
				Q.push((Node){npx, npy, hx, hy, dir});
			}

			// move hand
			for (int dx = -1; dx <= 1; ++dx) for (int dy = -1; dy <= 1; ++dy) {
				int nhx = hx + dx;
				int nhy = hy + dy;
				if ( inRange2(nhx, nhy) && Wall(hx, hy) ) {
					Q.push((Node){px, py, nhx, nhy, dir});
				}
			}

			// change dir / turn
			Q.push((Node){px, py, hx, hy, (dir+1)%4});
			Q.push((Node){px, py, hx, hy, (dir-1+4)%4});
		}
		int s = 0;
		for (int y = 0; y < H; ++y) {
			for (int x = 0; x < W; ++x) {
				s += used[y][x];
			}
		}
		if (used[gy][gx] && (ans < 0 || s < ans)) {
			ans = s;
		}
//		cout << used[gy][gx] << " " << s << endl << endl;
	}
	cout << ans << endl;
}
accuracy: 0.8666666666666667
time_ms: 30
memory_kb: 26648
final_rank: 14

code_snippet: #include <bits/stdc++.h>

using namespace std;

int Dx[4] = {0, 1, 0, -1};
int Dy[4] = {1, 0, -1, 0};

int dhx[4][4] = {
	{0, 1, 1, 1},
	{1, 1, 0, -1},
	{0, -1, -1, -1},
	{-1, -1, 0, 1},
};
int dhy[4][4] = {
	{1, 1, 0, -1},
	{0, -1, -1, -1},
	{-1, -1, 0, 1},
	{0, 1, 1, 1},
};

struct Node {
	int x, y, hx, hy, dir;
};

int H, W;
int wall[50][50] = {0};
bool used[50][50] = {0};
bool reach[50][50][51][51][4] = {0};
bool inRange(int x, int y) {
	return 0 <= x && x < W && 0 <= y && y < H;
}
bool inRange2(int x, int y) {
	return -1 <= x && x <= W && -1 <= y && y <= H;
}
bool Wall(int x, int y) {
	if (inRange(x, y)) return wall[y][x];
	if (inRange2(x, y)) return true;
	return false;
}
bool isInvalidHand(int px, int py, int hx, int hy, int dir) {
//	cout << ":" << px << " " << py << " " << hx << " " << hy << endl;
	if (!Wall(hx, hy)) return true;
	for (int i = 0; i < 4; ++i) {
		int x = px + dhx[dir][i];
		int y = py + dhy[dir][i];
		if (inRange2(x, y) && hx == x && hy == y) {
			return false;
		}
	}
	return true;
}

int main() {
	cin >> H >> W;

	for (int i = 0; i < 4; ++i) {
		Dy[i] = -Dy[i];
		for (int j = 0; j < 4; ++j) {
			dhy[i][j] = -dhy[i][j];
		}
	}

	int sx = -1, sy = -1, sd = -1;
	int gx = -1, gy = -1;
	for (int y = 0; y < H; ++y) {
		string str; cin >> str;
		for (int x = 0; x < W; ++x) {
			switch (str[x]) {
			case '#': wall[y][x] = true; break;
			case 'G': gx = x, gy = y; break;
			case '^': sx = x, sy = y; sd = 0; break;
			case '>': sx = x, sy = y; sd = 1; break;
			case 'v': sx = x, sy = y; sd = 2; break;
			case '<': sx = x, sy = y; sd = 3; break;
			}
		}
	}
	int ans = -1;
	for (int i = 0; i < 4; ++i) {
		queue<Node> Q;
		fill(used[0], used[50], false);
		fill(reach[0][0][0][0], reach[49][49][50][51], false);
		{
			int x = sx + dhx[sd][i];
			int y = sy + dhy[sd][i];
			Q.push((Node){sx, sy, x, y, sd});
		}
		while ( !Q.empty() ) {
			Node node = Q.front(); Q.pop();
			int px = node.x, py = node.y, hx = node.hx, hy = node.hy, dir = node.dir;
			if ( !inRange(px, py) ) continue;
			if ( wall[py][px] ) continue;
			if ( !inRange2(hx, hy) ) continue;
			if ( reach[py][px][hy+1][hx+1][dir] ) continue;
			if ( isInvalidHand(px, py, hx, hy, dir) ) continue;
			reach[py][px][hy+1][hx+1][dir] = true;
			used[py][px] = true;
			if (px == gx && py == gy) {
				break;
			}
//			cout << px << " " << py << " " << hx << " " << hy << " " << dir << endl;

			// move player
			{
				int npx = px + Dx[dir];
				int npy = py + Dy[dir];
				Q.push((Node){npx, npy, hx, hy, dir});
			}

			// move hand
			for (int dx = -1; dx <= 1; ++dx) for (int dy = -1; dy <= 1; ++dy) {
				int nhx = hx + dx;
				int nhy = hy + dy;
				if ( inRange2(nhx, nhy) && Wall(hx, hy) ) {
					Q.push((Node){px, py, nhx, nhy, dir});
				}
			}

			// change dir / turn
			Q.push((Node){px, py, hx, hy, (dir+1)%4});
			Q.push((Node){px, py, hx, hy, (dir-1+4)%4});
		}
		int s = 0;
		for (int y = 0; y < H; ++y) {
			for (int x = 0; x < W; ++x) {
				s += used[y][x];
			}
		}
		if (used[gy][gx] && (ans < 0 || s < ans)) {
			ans = s;
		}
//		cout << used[gy][gx] << " " << s << endl << endl;
	}
	cout << ans << endl;
}
accuracy: 0.8666666666666667
time_ms: 30
memory_kb: 26648
final_rank: 14