#include <bits/stdc++.h>
using namespace std;
int isCycle = 0;
const int N = 4e5;
vector<int> adj[N];
vector<int> val(N, 0);
vector<int> vis(N, 0);
vector<int> clr(N, 0);
vector<vector<int> > dp(N, vector<int>(30, 0));
bool dfs(int u) {
  vis[u] = 1;
  clr[u] = 1;
  for (int v : adj[u]) {
    if (!vis[v]) {
      bool flag = dfs(v);
      if (flag) return true;
    } else if (clr[v] == 1)
      return true;
    for (int i = 0; i <= 25; i++) dp[u][i] = max(dp[u][i], dp[v][i]);
  }
  dp[u][val[u]] += 1;
  clr[u] = 2;
  return false;
}
int main() {
  int n, m;
  cin >> n >> m;
  string s;
  cin >> s;
  for (int i = 0; i < s.size(); i++) val[i + 1] = s[i] - 'a';
  for (int i = 1; i <= m; i++) {
    int x, y;
    cin >> x >> y;
    adj[x].push_back(y);
    if (x == y) isCycle = 1;
  }
  if (isCycle == 1) {
    cout << -1 << "\n";
    return 0;
  }
  vector<int> mxPath(30, 0);
  for (int i = 1; i <= n; i++) {
    if (!vis[i]) {
      bool flag = dfs(i);
      if (flag) {
        cout << -1 << "\n";
        return 0;
      }
    }
    for (int j = 0; j < 26; j++) mxPath[j] = max(mxPath[j], dp[i][j]);
  }
  int mx = -1;
  for (int i = 0; i < 26; i++) mx = max(mx, mxPath[i]);
  cout << mx << "\n";
  return 0;
}
