#include <bits/stdc++.h>
using namespace std;
const long long M = 998244353;
long long modpow(long long n, long long k) {
  long long ans = 1;
  while (k) {
    if (k & 1) ans = (ans * n) % M;
    n = (n * n) % M;
    k >>= 1;
  }
  return ans;
}
long long ft[5005], ftinv[5005];
void init() {
  ft[0] = 1;
  for (int i = 1; i <= 5000; i++) {
    ft[i] = (ft[i - 1] * i) % M;
  }
  ftinv[5000] = modpow(ft[5000], M - 2);
  for (int i = 4999; i >= 0; i--) {
    ftinv[i] = (ftinv[i + 1] * (i + 1)) % M;
  }
}
long long nCk(int n, int k) {
  if (k < 0) {
    if (n < 0)
      return 1;
    else
      return 0;
  }
  long long p = ft[n];
  long long q = (ftinv[k] * ftinv[n - k]) % M;
  return (p * q) % M;
}
void solve() {
  int n;
  cin >> n;
  vector<int> odd, even;
  for (int i = 0; i < n; i++) {
    string s;
    cin >> s;
    int dif = 0;
    for (int j = 0; j < s.size(); j++) {
      if (j % 2)
        dif -= (s[j] - '0');
      else
        dif += (s[j] - '0');
    }
    dif %= 11;
    if (dif < 0) dif += 11;
    if (s.size() % 2)
      odd.push_back(dif);
    else
      even.push_back(dif);
  }
  if (odd.size() % 2)
    for (int &i : even) i = (11 - i);
  int o = odd.size(), e = even.size();
  int need = o / 2;
  long long dp[n + 1][11], nxt[n + 1][11];
  memset(dp, 0, sizeof(dp));
  dp[0][0] = 1;
  for (int v : odd) {
    memset(nxt, 0, sizeof(nxt));
    for (int i = 0; i <= need; i++) {
      for (int j = 0; j < 11; j++) {
        if (i < need)
          nxt[i + 1][(j + (11 - v)) % 11] =
              (nxt[i + 1][(j + (11 - v)) % 11] + dp[i][j]) % M;
        nxt[i][(j + v) % 11] = (nxt[i][(j + v) % 11] + dp[i][j]) % M;
      }
    }
    for (int i = 0; i <= need; i++) {
      for (int j = 0; j < 11; j++) {
        dp[i][j] = nxt[i][j];
      }
    }
  }
  vector<long long> anso(11);
  for (int i = 0; i < 11; i++) {
    int f1 = need, f2 = odd.size() - need;
    long long af = dp[need][i];
    af = (af * ft[f1]) % M;
    af = (af * ft[f2]) % M;
    anso[i] = af;
  }
  int evpos = (o + 1) / 2, odpos = (o + 1) - evpos;
  memset(dp, 0, sizeof(dp));
  dp[0][0] = 1;
  for (int v : even) {
    memset(nxt, 0, sizeof(nxt));
    for (int i = 0; i <= e; i++) {
      for (int j = 0; j < 11; j++) {
        if (i < e)
          nxt[i + 1][(j + (11 - v)) % 11] =
              (nxt[i + 1][(j + (11 - v)) % 11] + dp[i][j]) % M;
        nxt[i][(j + v) % 11] = (nxt[i][(j + v) % 11] + dp[i][j]) % M;
      }
    }
    for (int i = 0; i <= e; i++) {
      for (int j = 0; j < 11; j++) {
        dp[i][j] = nxt[i][j];
      }
    }
  }
  vector<long long> anse(11);
  for (int i = 0; i < 11; i++) {
    long long tmp = 0;
    for (int j = 0; j <= e; j++) {
      long long way1 = 1;
      way1 = (way1 * ft[j]) % M;
      way1 = (way1 * nCk(j + evpos - 1, evpos - 1)) % M;
      long long way2 = 1;
      way2 = (way2 * ft[e - j]) % M;
      way2 = (way2 * nCk((e - j) + odpos - 1, odpos - 1)) % M;
      long long af = way1 * way2 % M;
      af = (af * dp[j][i]) % M;
      tmp = (tmp + af) % M;
    }
    anse[i] = tmp;
  }
  long long final_ans = 0;
  for (int i = 0; i < 11; i++) {
    int j = (11 - i) % 11;
    final_ans = (final_ans + anso[i] * anse[j]) % M;
  }
  cout << final_ans << '\n';
}
signed main() {
  ios::sync_with_stdio(0);
  cin.tie(0);
  init();
  int t;
  cin >> t;
  while (t--) {
    solve();
  }
  return 0;
}
