#include <bits/stdc++.h>
using namespace std;
template <typename T>
struct persistent_array {
  int tree_n = 0;
  vector<pair<int, int>> tree;
  vector<T> values;
  persistent_array(int n = 0, int reserve_size = 0) {
    if (n > 0) init(n, reserve_size);
  }
  persistent_array(const vector<T> &v, int reserve_size = 0) {
    init(v, reserve_size);
  }
  void init(int n, int reserve_size = 0) {
    init(vector<T>(n, 0), reserve_size);
  }
  void set_children(int position, int left, int right) {
    tree[position] = {left, right};
  }
  void set_left(int position, int left) { tree[position].first = left; }
  void set_right(int position, int right) { tree[position].second = right; }
  int build_tree(int start, int end) {
    if (start >= end) return -1;
    int node = (int)tree.size();
    tree.emplace_back();
    if (end - start == 1) {
      set_children(node, start, start);
      return node;
    }
    int mid = (start + end) / 2;
    set_children(node, build_tree(start, mid), build_tree(mid, end));
    return node;
  }
  void init(const vector<T> &v, int reserve_size = 0) {
    tree_n = (int)v.size();
    values = v;
    tree.clear();
    if (reserve_size > 0) tree.reserve(reserve_size);
    build_tree(0, tree_n);
  }
  T query(int root, int index) {
    assert(0 <= index && index < tree_n);
    int current = root;
    int start = 0, end = tree_n;
    while (end - start > 1) {
      int mid = (start + end) / 2;
      if (index < mid) {
        current = tree[current].first;
        end = mid;
      } else {
        current = tree[current].second;
        start = mid;
      }
    }
    assert(start == index && end == index + 1);
    return values[tree[current].first];
  }
  int make_copy(int position) {
    assert(0 <= position && position < (int)tree.size());
    tree.push_back(tree[position]);
    return (int)tree.size() - 1;
  }
  int update_tree(int position, int start, int end, int index, T value) {
    assert(start < end);
    position = make_copy(position);
    if (end - start == 1) {
      assert(start == index);
      set_children(position, (int)values.size(), (int)values.size());
      values.push_back(value);
      return position;
    }
    int mid = (start + end) / 2;
    if (index < mid)
      set_left(position,
               update_tree(tree[position].first, start, mid, index, value));
    else
      set_right(position,
                update_tree(tree[position].second, mid, end, index, value));
    return position;
  }
  int update(int root, int index, T value) {
    assert(0 <= index && index < tree_n);
    return update_tree(root, 0, tree_n, index, value);
  }
};
const int INF = 1e9 + 5;
void solve_case() {
  int N;
  cin >> N;
  vector<int> A(N);
  for (int &a : A) {
    cin >> a;
    a--;
  }
  vector<int> jumps(N + 1, 0);
  persistent_array<int> closest(vector<int>(N, INF));
  vector<int> roots(N + 1, 0);
  long long answer = 0;
  for (int i = N - 1; i >= 0; i--) {
    int location = closest.query(roots[i + 1], A[i]);
    if (location < N) {
      assert(A[i] == A[location]);
      jumps[i] = jumps[location + 1] + 1;
    }
    answer += jumps[i];
    location = min(location + 1, N);
    roots[i] = closest.update(roots[location], A[i], i);
  }
  cout << answer << '\n';
}
int main() {
  ios::sync_with_stdio(false);
  cin.tie(nullptr);
  int Q;
  cin >> Q;
  while (Q-- > 0) solve_case();
}
