#include<bits/stdc++.h>
using namespace std;
struct edge
{
int u, v;
};
int n, m, cnt, cnt2;
int low[100005], dfn[100005], s[100005], a[100005];
int in[100005], dis[100005];
vector<edge> G[100005], G2[100005];
bool instack[100005];
stack<int> stk;
void tarjan(int u)
{
cnt ++;
dfn[u] = low[u] = cnt;
instack[u] = true;
stk.push(u);
for (int i = 0 ; i < G[u].size() ; i ++)
{
int v = G[u][i].v;
if (!dfn[v])
{
tarjan(v);
low[u] = min(low[u], low[v]);
}
else if (instack[v])
{
low[u] = min(low[u], dfn[v]);
}
}
if (low[u] == dfn[u])
{
int node;
while (node = stk.top())
{
instack[node] = false;
s[node] = u;
if (node == u)
{
break;
}
a[u] += a[node];
stk.pop();
}
}
}
int topo()
{
queue<int> que;
for (int i = 1 ; i <= n ; i ++)
{
if (in[i] == 0 && s[i] == i)
{
que.push(i);
dis[i] = a[i];
}
}
while (!que.empty())
{
int k = que.front();
que.pop();
for (int i = 1 ; i <= G2[k].size() ; i ++)
{
int v = G2[k][i].v;
dis[v] = max(dis[v], dis[k] + a[v]);
in[v] --;
if(in[v] == 0)
{
que.push(v);
}
}
}
int ans = 0;
for(int i = 1 ; i <= n ; i ++)
{
ans = max(ans, dis[i]);
}
return ans;
}
int main()
{
cin >> n >> m;
for (int i = 1 ; i <= n ; i ++)
{
cin >> a[i];
}
for (int i = 1 ; i <= m ; i ++)
{
int x, y;
cin >> x >> y;
G[x].push_back({x, y});
}
for (int i = 1 ; i <= n ; i ++)
{
if (!dfn[i])
{
tarjan(i);
}
}
for (int i = 1 ; i <= m ; i ++)
{
for (int j = 0 ; j < G[i].size() ; j ++)
{
int x = G[i][j].u, y = G[i][j].v;
int x2 = s[x], y2 = s[y];
if (x2 != y2)
{
G2[x2].push_back({x2, y2});
in[y2] ++;
}
}
}
cout << topo();
return 0;
}