#include <bits/stdc++.h>
using namespace std;
struct DSUrb {
  vector<int> e, off;
  void init(int n) {
    e = vector<int>(n, -1);
    off = vector<int>(n);
  }
  pair<int, int> get(int x) {
    int OFF = 0;
    while (e[x] >= 0) {
      OFF ^= off[x];
      x = e[x];
    }
    return make_pair(x, OFF);
  }
  vector<array<int, 4>> roll;
  int Union(int _x, int _y) {
    pair<int, int> x = get(_x);
    pair<int, int> y = get(_y);
    if (x.first == y.first) {
      if (x.second == y.second) return 0;
      roll.push_back({-1, -1, -1, -1});
      return 1;
    }
    if (e[x.first] > e[y.first]) swap(x, y);
    roll.push_back({x.first, y.first, e[x.first], e[y.first]});
    e[x.first] += e[y.first];
    e[y.first] = x.first;
    off[y.first] = x.second ^ y.second ^ 1;
    return 1;
  }
  void rollback() {
    auto a = roll.back();
    roll.pop_back();
    if (a[0] != -1) e[a[0]] = a[2], e[a[1]] = a[3];
  }
} DSU;
const int N = 5e5 + 5;
int n, m, k, gr[N];
pair<int, int> edge[N];
map<pair<int, int>, vector<int>> connect;
int main() {
  ios_base::sync_with_stdio(false);
  cin.tie(nullptr);
  cin >> n >> m >> k;
  DSU.init(n + 1);
  for (int i = 1; i <= n; i++) cin >> gr[i];
  long long res = 1ll * k * (k - 1) / 2;
  vector<pair<int, int>> cons;
  vector<bool> kt(k + 1, true);
  for (int i = 1; i <= m; i++) {
    cin >> edge[i].first >> edge[i].second;
    int gru = gr[edge[i].first];
    int grv = gr[edge[i].second];
    if (gru == grv) {
      if (!DSU.Union(edge[i].first, edge[i].second)) kt[gru] = false;
      continue;
    }
    if (gru > grv) swap(gru, grv);
    connect[make_pair(gru, grv)].push_back(i);
    cons.push_back(make_pair(gru, grv));
  }
  int cnt = 0;
  for (int i = 1; i <= k; i++)
    if (!kt[i]) cnt++;
  res -= (k - 1) * cnt;
  res += cnt * (cnt - 1) / 2;
  sort(cons.begin(), cons.end());
  cons.erase(unique(cons.begin(), cons.end()), cons.end());
  for (auto& x : cons) {
    int gru = x.first;
    int grv = x.second;
    if (!kt[gru] || !kt[grv]) continue;
    bool kt = true;
    int sz = DSU.roll.size();
    for (auto& i : connect[make_pair(gru, grv)]) {
      int u = edge[i].first;
      int v = edge[i].second;
      if (!DSU.Union(u, v)) {
        kt = false;
        break;
      }
    }
    if (!kt) res--;
    while (DSU.roll.size() > sz) DSU.rollback();
  }
  cout << res;
}
