#include <bits/stdc++.h>
#pragma GCC optimize("Ofast")
#pragma GCC target("avx,avx2,fma")
#pragma GCC optimization("unroll-loops")
using namespace std;
void __print(int x) { cerr << x; }
void __print(long x) { cerr << x; }
void __print(long long x) { cerr << x; }
void __print(unsigned x) { cerr << x; }
void __print(unsigned long x) { cerr << x; }
void __print(unsigned long long x) { cerr << x; }
void __print(float x) { cerr << x; }
void __print(double x) { cerr << x; }
void __print(long double x) { cerr << x; }
void __print(char x) { cerr << '\'' << x << '\''; }
void __print(const char *x) { cerr << '\"' << x << '\"'; }
void __print(const string &x) { cerr << '\"' << x << '\"'; }
void __print(bool x) { cerr << (x ? "true" : "false"); }
template <typename T, typename V>
void __print(const pair<T, V> &x) {
  cerr << '{';
  __print(x.first);
  cerr << ',';
  __print(x.second);
  cerr << '}';
}
template <typename T>
void __print(const T &x) {
  int f = 0;
  cerr << '{';
  for (auto &i : x) cerr << (f++ ? "," : ""), __print(i);
  cerr << "}";
}
void _print() { cerr << "]\n"; }
template <typename T, typename... V>
void _print(T t, V... v) {
  __print(t);
  if (sizeof...(v)) cerr << ", ";
  _print(v...);
}
template <typename T>
struct seg_tree_range_query {
  vector<T> tr;
  vector<T> a;
  void build(int l, int r, int v = 1) {
    if (l == r) {
      tr[v] = a[r];
      return;
    }
    int mid = (l + r) / 2;
    build(l, mid, 2 * v);
    build(mid + 1, r, 2 * v + 1);
    tr[v] = min(tr[2 * v], tr[2 * v + 1]);
  }
  void update(int l, int r, int pos, T val, int v = 1) {
    if (pos < l || pos > r) return;
    if (l == r && l == pos) {
      tr[v] = val;
      return;
    } else if (l == r)
      return;
    int mid = (l + r) / 2;
    update(l, mid, pos, val, 2 * v);
    update(mid + 1, r, pos, val, 2 * v + 1);
    tr[v] = min(tr[2 * v + 1], tr[2 * v]);
  }
  T query(int l, int r, int st, int end, int v = 1) {
    if (st > end) return (int)1e6;
    if (l == st && r == end) return tr[v];
    int mid = (l + r) / 2;
    T t1 = query(l, mid, st, min(mid, end), 2 * v);
    T t2 = query(mid + 1, r, max(st, mid + 1), end, 2 * v + 1);
    return min(t1, t2);
  }
};
void solve() {
  ios::sync_with_stdio(false);
  cin.tie(0);
  cout.tie(0);
  int n, m;
  cin >> n >> m;
  int a, b;
  vector<pair<int, int>> foe;
  vector<int> perm(n);
  vector<int> loc(n + 1);
  for (int i = 0; i < n; i++) {
    cin >> perm[i];
    loc[perm[i]] = i;
  }
  for (int i = 0; i < m; i++) {
    cin >> a >> b;
    a = loc[a];
    b = loc[b];
    if (a > b) {
      swap(a, b);
    }
    foe.push_back({a, b});
  }
  sort(foe.begin(), foe.end());
  foe.erase(unique(foe.begin(), foe.end()), foe.end());
  vector<int> en(m);
  for (int i = 0; i < m; i++) en[i] = foe[i].second;
  seg_tree_range_query<int> seg;
  seg.tr.resize(4 * m + 1);
  seg.a = en;
  seg.build(0, m - 1);
  ;
  long long int ans = n;
  for (int i = 0; i < n; i++) {
    int st =
        lower_bound(foe.begin(), foe.end(), make_pair(i, -1)) - foe.begin();
    int ed =
        lower_bound(foe.begin(), foe.end(), make_pair(foe[st].second, -1)) -
        foe.begin() - 1;
    if (st == (int)foe.size()) {
      ans += (n - i - 1);
      continue;
    }
    int fin_pos = seg.query(0, m - 1, st, ed);
    long long int inv = fin_pos - i;
    if (inv) {
      ans += inv - 1;
    };
  }
  cout << ans << "\n";
  return;
}
int main() {
  int t;
  t = 1;
  while (t--) solve();
  return 0;
}
