#include <bits/stdc++.h>
using namespace std;
using ll = long long;

ll solve_sub(ll N, string S, vector<ll>& A) {
    ll d_min = 1e5;
    for ( int i = 0; i < N; i++ ) {
        d_min = min(d_min, abs(A[i]-A[i+1]));
    }
    vector<ll> mn(N+1,0);
    for ( int i = 1; i <= N; i++ ) {
        if ( S[i-1] == '<' ) {
            mn[i] = max(mn[i],mn[i-1]+1);
        }
    }
    for ( int i = N-1; i >= 0; i-- ) {
        if ( S[i] == '>' ) {
            mn[i] = max(mn[i],mn[i+1]+1);
        }
    }
    
    ll k = d_min;
    vector<vector<ll>> ans(k, vector<ll>(N+1));
    for ( int j = 0; j < k; j++ ) {
        for ( int i = 0; i < N+1; i++ ) {
            ans[j][i] = A[i] / k + (j < A[i]%k ? 1 : 0) ;
        }
    }

    cout << k << "\n";
    for ( int j = 0; j < k; j++ ) {
        for ( int i = 0; i <= N; i++ ) {
            cout << ( i != 0 ? " " : "") << ans[j][i];
        }
        cout << "\n";
    }

    // debug
    vector<ll> b(N+1);
    for ( int i = 0; i <= N; i++ ) {
        b[i] = ans[k-1][i];
    }
    for ( int i = 0; i <= N; i++ ) {
        bool ok = true;
        if ( i > 0 ) {
            if ( b[i-1] < b[i] && S[i-1] == '>' ) ok = false;
            if ( b[i-1] > b[i] && S[i-1] == '<' ) ok = false;
            if ( b[i-1] == b[i] ) ok = false;
            if ( !ok ) {
                int z = 1;
            }
        }
        
    }
    for ( int i = 0; i <= N; i++ ) {
        b[i] = ans[0][i];
    }
    for ( int i = 0; i <= N; i++ ) {
        bool ok = true;
        if ( i > 0 ) {
            if ( b[i-1] < b[i] && S[i-1] == '>' ) ok = false;
            if ( b[i-1] > b[i] && S[i-1] == '<' ) ok = false;
            if ( b[i-1] == b[i] ) ok = false;
            if ( !ok ) {
                int z = 1;
            }
        }
        
    }

    return 0;
}

ll solve() {
    ll N;
    string S;
    cin >> N >> S;
    vector<ll> A(N+1);
    for ( int i = 0; i < N+1; i++ ) cin >> A[i];
    ll ans = solve_sub(N,S,A);
    return ans;
}

struct Data {
    int id;
    ll N;
    string S;
    vector<ll> A;
};
void test() {
    mt19937_64 mt64(0);
    uniform_int_distribution<ll> rnd_n(3, 3);
    uniform_int_distribution<ll> rnd_v(2, 20);

    int id = 0;
    vector<Data> ts;
    ts.push_back({++id,3,"<><",{3,8,6,10}});
    ts.push_back({++id,3,"<<>",{0,2,4,2}});
    for ( int i = 0; i < 100; i++ ) {
        int n = rnd_n(mt64);
        vector<ll> a;
        for ( int j = 0; j < n+1; j++ ) {
            a.push_back(rnd_v(mt64));
        }
        string s;
        for ( int j = 0; j < n; j++ ) {
            if ( a[j] == a[j+1] ) a[j+1]++;
            char c = a[j] < a[j+1] ? '<' : '>';
            s.push_back(c);
        }
        ts.push_back({++id,n,s,a});
    }
    
    for ( Data& t : ts ) {
        auto ans0 = solve_sub(t.N, t.S, t.A);
        if ( ans0 >= 0 ) {
            int z = 1;
        }

        // auto ans1 = solve_small_1(t.N,t.S,t.A);
        // if ( ans0 != ans1 ) {
        //     cout << t.id << " " << ans0 << " " << ans1 << "\n";
        // }
    }
    cout << "end" << "\n";
}



int main() {
    // test();

    solve();
    return 0;
}
#include <bits/stdc++.h>

#define ll long long
#define map unordered_map
#define set unordered_set
#define l_l pair<ll, ll>
#define P pair<ll, ll>
#define vll vector<ll>
#define mll map<ll, ll>
#define mp make_pair
#define rep(i, n) for (int i = 0, i##_len = (n); i < i##_len; ++i)
#define reps(i, n) for (int i = 1, i##_len = (n); i <= i##_len; ++i)
#define rev(i, n) for (int i = ((int)(n)-1); i >= 0; --i)
#define revs(i, n) for (int i = ((int)(n)); i > 0; --i)
// template<class T>bool chmax(T &a, const T &b) { if (a<b) { a=b; return 1; } return 0; }
// template<class T>bool chmin(T &a, const T &b) { if (b<a) { a=b; return 1; } return 0; }

using namespace std;

const ll MOD = 1000000007LL;
const ll INF = (1LL << 60LL);

// template <class T> void plus_mod(T &a, const T &b) {a = (a + b) % MOD;}

vector<P> warps[30];

ll warp_points[2010][2010];

ll maze[2010][2010];

vector<P> get_warp(ll y, ll x) {
  ll wid = warp_points[y][x];

  return warps[wid];

  // auto point1 = warps[wid][0];
  // auto point2 = warps[wid][1];

  // if (point1.first == y && point1.second == x) {
  //   return point2;
  // } else {
  //   return point1;
  // }
}

int main() {
  // std::cout << std::fixed << std::setprecision(10);

  ll H, W;
  scanf("%lld %lld", &H, &W);

  fill(maze[0], maze[2005], -1);

  ll sy, sx, gy, gx;

  // インデックス1開始なので注意
  reps(y, H) {
    string line;
    cin >> line;

    reps(x, line.size()) {
      char ch = line[x - 1];
      if (ch == '#') {
        maze[y][x] = -1;
      } else if (ch == '.') {
        maze[y][x] = INF;
      } else if (ch == 'S') {
        sy = y;
        sx = x;
        maze[y][x] = 0;
      } else if (ch == 'G') {
        gy = y;
        gx = x;
        maze[y][x] = INF;
      } else {
        // ワープ
        ll wid = ch - 'a' + 1;
        warps[wid].emplace_back(mp(y, x));
        warp_points[y][x] = wid;

        maze[y][x] = INF;
      }
    }
  }

  //--------------------------------------------------

  deque<l_l> que;
  que.emplace_back(mp(sy, sx));
  maze[sy][sx] = 0;

  for (;;) {
    if (que.empty()) {
      break;
    }
    auto pos = que.front();
    que.pop_front();
    ll y = pos.first;
    ll x = pos.second;

    // cout << "y:" << (y) << ",x:" << (x) << endl;

    ll c = maze[y][x];

    for (auto e : {mp(y - 1, x), mp(y, x - 1), mp(y + 1, x), mp(y, x + 1)}) {
      if (maze[e.first][e.second] == -1) {
        continue;
      }
      if (maze[e.first][e.second] <= c + 1) {
        continue;
      }
      maze[e.first][e.second] = c + 1;
      que.emplace_back(make_pair(e.first, e.second));
    }

    if (warp_points[y][x]) {
      ll wid = warp_points[y][x];

      auto warp_list = get_warp(y, x);

      rep(i, warp_list.size()) {
        auto next = warp_list[i];

        warp_points[next.first][next.second] = 0;

        if (maze[next.first][next.second] > c + 1) {
          // cout << "WARP!:"
          //      << "next.first:" << (next.first) << ",next.second:" << (next.second) << endl;
          maze[next.first][next.second] = c + 1;
          que.emplace_front(make_pair(next.first, next.second));
        }

        warp_points[next.first][next.second] = 0;
      }
    }
  }

  ll ans = maze[gy][gx];

  if (ans == INF) {
    cout << (-1) << endl;
    return 0;
  }
  cout << ans << endl;
}
