Now that you have proposed a fake post for the HC2 Facebook page, Heidi wants to measure the quality of the post before actually posting it. She recently came across a (possibly fake) article about the impact of fractal structure on multimedia messages and she is now trying to measure the self-similarity of the message, which is defined aswhere the sum is over all nonempty strings p and  is the number of occurences of p in s as a substring. (Note that the sum is infinite, but it only has a finite number of nonzero summands.)Heidi refuses to do anything else until she knows how to calculate this self-similarity. Could you please help her? (If you would like to instead convince Heidi that a finite string cannot be a fractal anyway – do not bother, we have already tried.)

The input starts with a line indicating the number of test cases T (1 ≤ T ≤ 10). After that, T test cases follow, each of which consists of one line containing a string s (1 ≤ |s| ≤ 100 000) composed of lowercase letters (a-z).

Output T lines, every line containing one number – the answer to the corresponding test case.

NoteA string s contains another string p as a substring if p is a contiguous subsequence of s. For example, ab is a substring of cab but not of acb.

/+ dub.sdl:
    name "I"
    dependency "dcomp" version=">=0.6.0"
+/

import std.stdio, std.algorithm, std.range, std.conv;
// import dcomp.foundation, dcomp.scanner;
// import dcomp.array;
// import dcomp.algorithm;
// import dcomp.string;
// import dcomp.datastructure.lazyseg;
// import dcomp.container.deque;

void solve() {
    string s;
    sc.read(s);
    auto saInfo = suffixArray(s);
    int n = s.length.to!int;
    auto tr = LazySeg!(long[2], int, (a, b)=>[a[0]+b[0], a[1]+b[1]].fixed, (a, b)=>[b * a[1], a[1]].fixed, (a, b)=>b, [0L, 1L].fixed, -1)(n);
    tr[0..n] += 10^^9;
    long sm = 0;
    Deque!(int[2]) deq;
    deq.insertBack([-1, 0]);
    foreach (i; 1..n) {
        auto u = saInfo.lcp[i];
        while (deq.back[0] >= u) deq.removeBack;
//        auto le = binSearch!(x => tr.single(x)[0] >= u)(-1, i);
        auto le = deq.back[1];
//        writeln(le, " ", le2, " ", deq);
        tr[le..i] += u;
        sm += tr[0..i].sum[0];
        deq.insertBack([u, i]);
//        writeln(tr);
    }
    writeln(sm*2 + long(n)*(n+1)/2);
}

int main() {
    int n;
    sc.read(n);
    foreach (i; 0..n) {
        solve();
    }
    return 0;
}

Scanner sc;
static this() {
    sc = new Scanner(stdin);
}
/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/container/deque.d */
// module dcomp.container.deque;

struct Deque(T, bool mayNull = true) {
    import core.exception : RangeError;
    import core.memory : GC;
    import std.range : ElementType, isInputRange;
    import std.traits : isImplicitlyConvertible;

    struct Payload {
        T *d;
        size_t st, length, cap;
        @property bool empty() const { return length == 0; }
        alias opDollar = length;
        ref inout(T) opIndex(size_t i) inout {
            version(assert) if (length <= i) throw new RangeError();
            return d[(st+i >= cap) ? (st+i-cap) : st+i];
        }
        private void expand() {
            import std.algorithm : max;
            assert(length == cap);
            auto nc = max(size_t(4), 2*cap);
            T* nd = cast(T*)GC.malloc(nc * T.sizeof);
            foreach (i; 0..length) {
                nd[i] = this[i];
            }
            d = nd; st = 0; cap = nc;
        }
        void clear() {
            st = length = 0;
        }
        void insertFront(T v) {
            if (length == cap) expand();
            if (st == 0) st += cap;
            st--; length++;
            this[0] = v;
        }
        void insertBack(T v) {
            if (length == cap) expand();
            length++;
            this[length-1] = v;
        }
        void removeFront() {
            assert(!empty, "Deque.removeFront: Deque is empty");
            st++; length--;
            if (st == cap) st = 0;
        }
        void removeBack() {
            assert(!empty, "Deque.removeBack: Deque is empty");
            length--;
        }
    }
    struct RangeT(A) {
        alias T = typeof(*(A.p));
        alias E = typeof(A.p.d[0]);
        T *p;
        size_t a, b;
        @property bool empty() const { return b <= a; }
        @property size_t length() const { return b-a; }
        @property RangeT save() { return RangeT(p, a, b); }
        @property RangeT!(const A) save() const {
            return typeof(return)(p, a, b);
        }
        alias opDollar = length;
        @property ref inout(E) front() inout { return (*p)[a]; }
        @property ref inout(E) back() inout { return (*p)[b-1]; }
        void popFront() {
            version(assert) if (empty) throw new RangeError();
            a++;
        }
        void popBack() {
            version(assert) if (empty) throw new RangeError();
            b--;
        }
        ref inout(E) opIndex(size_t i) inout { return (*p)[i]; }
        RangeT opSlice() { return this.save; }
        RangeT opSlice(size_t i, size_t j) {
            version(assert) if (i > j || a + j > b) throw new RangeError();
            return typeof(return)(p, a+i, a+j);
        }
        RangeT!(const A) opSlice() const { return this.save; }
        RangeT!(const A) opSlice(size_t i, size_t j) const {
            version(assert) if (i > j || a + j > b) throw new RangeError();
            return typeof(return)(p, a+i, a+j);
        }
    }

    alias Range = RangeT!Deque;
    alias ConstRange = RangeT!(const Deque);
    alias ImmutableRange = RangeT!(immutable Deque);

    Payload* p;
    private void I() { if (mayNull && !p) p = new Payload(); }
    private void C() const {
        version(assert) if (mayNull && !p) throw new RangeError();
    }
    static if (!mayNull) {
        @disable this();
    }

    private this(Payload* p) {
        this.p = p;
    }
    this(U)(U[] values...) if (isImplicitlyConvertible!(U, T)) {
        p = new Payload();
        foreach (v; values) {
            insertBack(v);
        }
    }

    this(Range)(Range r)
    if (isInputRange!Range &&
    isImplicitlyConvertible!(ElementType!Range, T) &&
    !is(Range == T[])) {
        p = new Payload();
        foreach (v; r) {
            insertBack(v);
        }
    }
    static Deque make() { return Deque(new Payload()); }
    @property bool havePayload() const { return (!mayNull || p); }
    @property bool empty() const { return (!havePayload || p.empty); }
    @property size_t length() const { return (havePayload ? p.length : 0); }
    alias opDollar = length;
    ref inout(T) opIndex(size_t i) inout {C; return (*p)[i]; }
    ref inout(T) front() inout {C; return (*p)[0]; }
    ref inout(T) back() inout {C; return (*p)[$-1]; }
    void clear() { if (p) p.clear(); }
    void insertFront(T v) {I; p.insertFront(v); }
    void insertBack(T v) {I; p.insertBack(v); }
    void removeFront() {C; p.removeFront(); }
    void removeBack() {C; p.removeBack(); }
    Range opSlice() {I; return Range(p, 0, length); }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/array.d */
// module dcomp.array;

T[N] fixed(T, size_t N)(T[N] a) {return a;}

struct FastAppender(A) {
    import std.algorithm : max;
    import std.range.primitives : ElementEncodingType;
    import core.stdc.string : memcpy;

    private alias T = ElementEncodingType!A;
    private T* _data;
    private size_t len, cap;

    @property size_t length() {return len;}

    void reserve(size_t nlen) {
        import core.memory : GC;
        if (nlen <= cap) return;

        void* nx = GC.malloc(nlen * T.sizeof);

        cap = nlen;
        if (len) memcpy(nx, _data, len * T.sizeof);
        _data = cast(T*)(nx);
    }

    void opOpAssign(string op : "~")(T item) {
        if (len == cap) {
            reserve(max(4, cap*2));
        }
        _data[len++] = item;
    }

    void clear() {
        len = 0;
    }

    T[] data() {
        return (_data) ? _data[0..len] : null;
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/datastructure/lazyseg.d */
// module dcomp.datastructure.lazyseg;

struct LazySeg(T, L, alias opTT, alias opTL, alias opLL, T eT, L eL) {
    const int n, sz, lg;
    T[] d;
    L[] lz;
    @disable this();
    this(int n) {
        import std.algorithm : fill, each;
        import core.bitop : bsr;
        if (n == 0) return;
        int lg = n.bsr;
        if ((2^^lg) < n) lg++;
        this.n = n;
        this.sz = 2^^lg;
        this.lg = lg;
        d = new T[](2*this.sz);
        d.each!((ref x) => x = eT);
        lz = new L[](2*this.sz);
        lz.each!((ref x) => x = eL);
    }
    private void lzAdd(int k, L x) {
        d[k] = opTL(d[k], x);
        lz[k] = opLL(lz[k], x);
    }
    private void push(int k) {
        if (lz[k] == eL) return;
        lzAdd(2*k, lz[k]);
        lzAdd(2*k+1, lz[k]);
        lz[k] = eL;
    }
    T sum(int a, int b, int l, int r, int k) {
        if (b <= l || r <= a) return eT;
        if (a <= l && r <= b) return d[k];
        push(k);
        int md = (l+r)/2;
        return opTT(sum(a, b, l, md, 2*k),
            sum(a, b, md, r, 2*k+1));
    }
    T single(int k) {
        k += sz;
        foreach_reverse (int i; 1..lg+1) {
            push(k>>i);
        }
        return d[k];
    }
    T sum(int a, int b) {
        assert(0 <= a && a <= b && b <= n);
        return sum(a, b, 0, sz, 1);
    }
    void add(int a, int b, L x, int l, int r, int k) {
        if (b <= l || r <= a) return;
        if (a <= l && r <= b) {
            lzAdd(k, x);
            return;
        }
        push(k);
        int md = (l+r)/2;
        add(a, b, x, l, md, 2*k);
        add(a, b, x, md, r, 2*k+1);
        d[k] = opTT(d[2*k], d[2*k+1]);
    }
    void add(int a, int b, L x) {
        assert(0 <= a && a <= b && b <= n);
        add(a, b, x, 0, sz, 1);
    }
    @property int opDollar() const {return sz;}
    struct Range {
        LazySeg* seg;
        int start, end;
        @property T sum() {
            return seg.sum(start, end);
        }
    }
    int[2] opSlice(size_t dim)(int start, int end) {
        assert(0 <= start && start <= end && end <= sz);
        return [start, end];
    }
    Range opIndex(int[2] rng) {
        return Range(&this, rng[0], rng[1]);
    }
    void opIndexOpAssign(string op : "+")(L x, int[2] rng) {
        add(rng[0], rng[1], x);
    }
}
/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/string.d */
// module dcomp.string;

struct SA(T) {
    T[] s;

    int[] sa, rsa, lcp;
    this(in T[] s) {
        size_t n = s.length;
        this.s = s.dup;
        sa = new int[](n+1);
        rsa = new int[](n+1);
        lcp = new int[](n);
    }
}

int[] sais(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm, std.range;
    int n = _s.length.to!int;
    int[] sa = new int[](n+1);
    if (n == 0) return sa;

    auto s = _s.map!"a+1".array ~ T(0); B++;

    bool[] ls = new bool[](n+1);
    ls[n] = true;
    foreach_reverse (i; 0..n) {
        ls[i] = (s[i] == s[i+1]) ? ls[i+1] : (s[i] < s[i+1]);
    }

    int[] sumL = new int[](B+1), sumS = new int[](B+1);
    s.each!((i, c) => !ls[i] ? sumS[c]++ : sumL[c+1]++);
    foreach (i; 0..B) {
        sumL[i+1] += sumS[i];
        sumS[i+1] += sumL[i+1];
    }

    void induce(in int[] lms) {
        sa[] = -1;
        auto buf0 = sumS.dup;
        foreach (d; lms) {
            sa[buf0[s[d]]++] = d;
        }
        auto buf1 = sumL.dup;
        foreach (v; sa) {
            if (v >= 1 && !ls[v-1]) {
                sa[buf1[s[v-1]]++] = v-1;
            }
        }
        auto buf2 = sumL.dup;
        foreach_reverse (v; sa) {
            if (v >= 1 && ls[v-1]) {
                sa[--buf2[s[v-1]+1]] = v-1;
            }
        }
    }

    int[] lms = iota(1, n+1).filter!(i => !ls[i-1] && ls[i]).array;
    int[] lmsMap = new int[](n+1);
    lmsMap[] = -1; lms.each!((i, v) => lmsMap[v] = i.to!int);

    induce(lms);

    if (lms.length >= 2) {
        int m = lms.length.to!int - 1;

        auto lms2 = sa.filter!(v => lmsMap[v] != -1).array;
        int recN = 1;
        int[] recS = new int[](m);
        recS[lmsMap[lms2[1]]] = 1;
        foreach (i; 2..m+1) {
            int l = lms2[i-1], r = lms2[i];
            int nl = lms[lmsMap[l]+1], nr = lms[lmsMap[r]+1];
            if (cmp(s[l..nl+1], s[r..nr+1])) recN++;
            recS[lmsMap[lms2[i]]] = recN;
        }

        induce(lms.indexed(sais!int(recS, recN)).array);
    }

    return sa;
}

SA!T suffixArray(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm;
    int n = _s.length.to!int;
    auto saInfo = SA!T(_s);
    if (n == 0) return saInfo;

    with (saInfo) {
        sa = sais(_s, B);

        sa.each!((i, v) => rsa[v] = i.to!int);

        int h = 0;
        foreach (i; 0..n) {
            int j = sa[rsa[i]-1];
            if (h > 0) h--;
            for (; j+h < n && i+h < n; h++) {
                if (s[j+h] != s[i+h]) break;
            }
            lcp[rsa[i]-1] = h;
        }
    }
    return saInfo;
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/scanner.d */
// module dcomp.scanner;

class Scanner {
    import std.stdio : File;
    import std.conv : to;
    import std.range : front, popFront, array, ElementType;
    import std.array : split;
    import std.traits : isSomeChar, isStaticArray, isArray;
    import std.algorithm : map;
    File f;
    this(File f) {
        this.f = f;
    }
    char[512] lineBuf;
    char[] line;
    private bool succ() {
        import std.range.primitives : empty, front, popFront;
        import std.ascii : isWhite;
        while (true) {
            while (!line.empty && line.front.isWhite) {
                line.popFront;
            }
            if (!line.empty) break;
            if (f.eof) return false;
            line = lineBuf[];
            f.readln(line);
        }
        return true;
    }

    private bool readSingle(T)(ref T x) {
        import std.algorithm : findSplitBefore;
        import std.string : strip;
        import std.conv : parse;
        if (!succ()) return false;
        static if (isArray!T) {
            alias E = ElementType!T;
            static if (isSomeChar!E) {

                auto r = line.findSplitBefore(" ");
                x = r[0].strip.dup;
                line = r[1];
            } else {
                auto buf = line.split.map!(to!E).array;
                static if (isStaticArray!T) {

                    assert(buf.length == T.length);
                }
                x = buf;
                line.length = 0;
            }
        } else {
            x = line.parse!T;
        }
        return true;
    }
    int read(T, Args...)(ref T x, auto ref Args args) {
        if (!readSingle(x)) return 0;
        static if (args.length == 0) {
            return 1;
        } else {
            return 1 + read(args);
        }
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/algorithm.d */
// module dcomp.algorithm;

import std.range.primitives;
import std.traits : isFloatingPoint, isIntegral;

T binSearch(alias pred, T)(T l, T r) if (isIntegral!T) {
    while (r-l > 1) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

T binSearch(alias pred, T)(T l, T r, int cnt = 60) if (isFloatingPoint!T) {
    foreach (i; 0..cnt) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

E minimum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? a : b)(seed, range);
}

ElementType!Range minimum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return minimum!pred(range, e);
}

E maximum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? b : a)(seed, range);
}

ElementType!Range maximum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return maximum!pred(range, e);
}

Rotator!Range rotator(Range)(Range r) {
    return Rotator!Range(r);
}

struct Rotator(Range)
if (isForwardRange!Range && hasLength!Range) {
    size_t cnt;
    Range start, now;
    this(Range r) {
        cnt = 0;
        start = r.save;
        now = r.save;
    }
    this(this) {
        start = start.save;
        now = now.save;
    }
    @property bool empty() {
        return now.empty;
    }
    @property auto front() {
        assert(!now.empty);
        import std.range : take, chain;
        return chain(now, start.take(cnt));
    }
    @property Rotator!Range save() {
        return this;
    }
    void popFront() {
        cnt++;
        now.popFront;
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/ascii.d */
// module dcomp.ascii;

struct ASCIIString {
    string s;
    alias s this;
    this(string s) {
        this.s = s;
    }
    ref immutable(char) front() const {
        return s[0];
    }
    void popFront() {
        s = s[1..$];
    }
    ref immutable(char) back() const {
        return s[$-1];
    }
    void popBack() {
        s = s[0..$-1];
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/foundation.d */
// module dcomp.foundation;

static if (__VERSION__ <= 2070) {
    template fold(fun...) if (fun.length >= 1) {
        auto fold(R, S...)(R r, S seed) {
            import std.algorithm : reduce;
            static if (S.length < 2) {
                return reduce!fun(seed, r);
            } else {
                import std.typecons : tuple;
                return reduce!fun(tuple(seed), r);
            }
        }
    }

}
version (X86) static if (__VERSION__ < 2071) {
    int bsf(ulong v) {
        foreach (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int bsr(ulong v) {
        foreach_reverse (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int popcnt(ulong v) {
        int c = 0;
        foreach (i; 0..64) {
            if (v & (1UL << i)) c++;
        }
        return c;
    }
}

/+ dub.sdl:
    name "I"
    dependency "dcomp" version=">=0.6.0"
+/

import std.stdio, std.algorithm, std.range, std.conv, std.traits;
// import dcomp.foundation, dcomp.scanner;
// import dcomp.array;
// import dcomp.algorithm;
// import dcomp.string;

/// 遅延伝搬Segment Tree
struct LazySeg(T, L, alias opTT, alias opTL, alias opLL, T eT, L eL) {
    const int n, sz, lg;
    T[] d;
    L[] lz;
    @disable this();
    this(int n) {
        import std.algorithm : fill, each;
        import core.bitop : bsr;
        if (n == 0) return;
        int lg = n.bsr;
        if ((2^^lg) < n) lg++;
        this.n = n;
        this.sz = 2^^lg;
        this.lg = lg;
        d = new T[](2*this.sz);
        d.each!((ref x) => x = eT);
        lz = new L[](2*this.sz);
        lz.each!((ref x) => x = eL);
    }
    private void lzAdd(int k, L x) {
        d[k] = opTL(d[k], x);
        lz[k] = opLL(lz[k], x);
    }
    private void push(int k) {
        if (lz[k] == eL) return;
        lzAdd(2*k, lz[k]);
        lzAdd(2*k+1, lz[k]);
        lz[k] = eL;
    }
    //d[a]+d[a+1]+...+d[b-1]
    T sum(int a, int b, int l, int r, int k) {
        if (b <= l || r <= a) return eT;
        if (a <= l && r <= b) return d[k];
        push(k);
        int md = (l+r)/2;
        return opTT(sum(a, b, l, md, 2*k),
            sum(a, b, md, r, 2*k+1));
    }
    T single(int k) {
        k += sz;
        foreach_reverse (int i; 1..lg+1) {
            push(k>>i);
        }
        return d[k];
    }
    void singleSet(T x, int k) {
        k += sz;
        foreach_reverse (int i; 1..lg+1) {
            push(k>>i);
        }
        d[k] = x;
        foreach (int i; 1..lg+1) {
            d[k>>i] = opTT(d[2*(k>>i)], d[2*(k>>i)+1]);
        }
    }
    T sum(int a, int b) {
        assert(0 <= a && a <= b && b <= n);
        return sum(a, b, 0, sz, 1);
    }
    void add(int a, int b, L x, int l, int r, int k) {
        if (b <= l || r <= a) return;
        if (a <= l && r <= b) {
            lzAdd(k, x);
            return;
        }
        push(k);
        int md = (l+r)/2;
        add(a, b, x, l, md, 2*k);
        add(a, b, x, md, r, 2*k+1);
        d[k] = opTT(d[2*k], d[2*k+1]);
    }
    void add(int a, int b, L x) {
        assert(0 <= a && a <= b && b <= n);
        add(a, b, x, 0, sz, 1);
    }
    @property int opDollar() const {return sz;}
    struct Range {
        LazySeg* seg;
        int start, end;
        @property T sum() {
            return seg.sum(start, end);
        }
    }
    T opIndex(int k) {
        assert(0 <= k && k < n);
        return single(k);
    }
    void opIndexAssign(T x, int k) {
        assert(0 <= k && k < n);
        singleSet(x, k);
    }
    int[2] opSlice(size_t dim)(int start, int end) {
        assert(0 <= start && start <= end && end <= sz);
        return [start, end];
    }
    Range opIndex(int[2] rng) {
        return Range(&this, rng[0], rng[1]);
    }
    void opIndexOpAssign(string op : "+")(L x, int[2] rng) {
        add(rng[0], rng[1], x);
    }
}

int binSearchLeft(alias pred, TR)(TR t, int a, int b)
if (isInstanceOf!(LazySeg, TR)) {
    alias args = TemplateArgsOf!TR;
    alias opTT = args[2];
    with (t) {
        auto x = args[5];
        if (pred(x)) return a-1;
        int pos = a;
        void f(int a, int b, int l, int r, int k) {
            if (b <= l || r <= a) return;
            if (a <= l && r <= b && !pred(opTT(x, d[k]))) {
                x = opTT(x, d[k]);
                pos = r;
                return;
            }
            if (l+1 == r) return;
            push(k);
            int md = (l+r)/2;
            f(a, b, l, md, 2*k);
            if (pos >= md) f(a, b, md, r, 2*k+1);
        }
        f(a, b, 0, sz, 1);
        return pos;
    }
}

void solve() {
    string s;
    sc.read(s);
    auto saInfo = suffixArray(s);
    int n = s.length.to!int;
    import std.typecons;
    alias T = Tuple!(long, int, int);
    auto tr = LazySeg!(T, int,
        (a, b)=>T(a[0]+b[0], a[1]+b[1], max(a[2], b[2])),
        (a, b)=>T(long(b) * a[1], a[1], b),
        (a, b)=>b,
        T(0L, 1, -(10^^9)), -1)(n);
    tr[0..n] += 10^^9;
    long sm = 0;
    foreach (i; 1..n) {
        auto u = saInfo.lcp[i];
        auto le = tr.binSearchLeft!(x => x[2] >= u)(0, i);
        tr[le..i] += u;
        sm += tr[0..i].sum[0];
//        writeln(tr);
    }
    writeln(sm*2 + long(n)*(n+1)/2);
}

int main() {
    int n;
    sc.read(n);
    foreach (i; 0..n) {
        solve();
    }
    return 0;
}

Scanner sc;
static this() {
    sc = new Scanner(stdin);
}
/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/array.d */
// module dcomp.array;

T[N] fixed(T, size_t N)(T[N] a) {return a;}

struct FastAppender(A) {
    import std.algorithm : max;
    import std.range.primitives : ElementEncodingType;
    import core.stdc.string : memcpy;

    private alias T = ElementEncodingType!A;
    private T* _data;
    private size_t len, cap;

    @property size_t length() {return len;}

    void reserve(size_t nlen) {
        import core.memory : GC;
        if (nlen <= cap) return;

        void* nx = GC.malloc(nlen * T.sizeof);

        cap = nlen;
        if (len) memcpy(nx, _data, len * T.sizeof);
        _data = cast(T*)(nx);
    }

    void opOpAssign(string op : "~")(T item) {
        if (len == cap) {
            reserve(max(4, cap*2));
        }
        _data[len++] = item;
    }

    void clear() {
        len = 0;
    }

    T[] data() {
        return (_data) ? _data[0..len] : null;
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/string.d */
// module dcomp.string;

struct SA(T) {
    T[] s;

    int[] sa, rsa, lcp;
    this(in T[] s) {
        size_t n = s.length;
        this.s = s.dup;
        sa = new int[](n+1);
        rsa = new int[](n+1);
        lcp = new int[](n);
    }
}

int[] sais(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm, std.range;
    int n = _s.length.to!int;
    int[] sa = new int[](n+1);
    if (n == 0) return sa;

    auto s = _s.map!"a+1".array ~ T(0); B++;

    bool[] ls = new bool[](n+1);
    ls[n] = true;
    foreach_reverse (i; 0..n) {
        ls[i] = (s[i] == s[i+1]) ? ls[i+1] : (s[i] < s[i+1]);
    }

    int[] sumL = new int[](B+1), sumS = new int[](B+1);
    s.each!((i, c) => !ls[i] ? sumS[c]++ : sumL[c+1]++);
    foreach (i; 0..B) {
        sumL[i+1] += sumS[i];
        sumS[i+1] += sumL[i+1];
    }

    void induce(in int[] lms) {
        sa[] = -1;
        auto buf0 = sumS.dup;
        foreach (d; lms) {
            sa[buf0[s[d]]++] = d;
        }
        auto buf1 = sumL.dup;
        foreach (v; sa) {
            if (v >= 1 && !ls[v-1]) {
                sa[buf1[s[v-1]]++] = v-1;
            }
        }
        auto buf2 = sumL.dup;
        foreach_reverse (v; sa) {
            if (v >= 1 && ls[v-1]) {
                sa[--buf2[s[v-1]+1]] = v-1;
            }
        }
    }

    int[] lms = iota(1, n+1).filter!(i => !ls[i-1] && ls[i]).array;
    int[] lmsMap = new int[](n+1);
    lmsMap[] = -1; lms.each!((i, v) => lmsMap[v] = i.to!int);

    induce(lms);

    if (lms.length >= 2) {
        int m = lms.length.to!int - 1;

        auto lms2 = sa.filter!(v => lmsMap[v] != -1).array;
        int recN = 1;
        int[] recS = new int[](m);
        recS[lmsMap[lms2[1]]] = 1;
        foreach (i; 2..m+1) {
            int l = lms2[i-1], r = lms2[i];
            int nl = lms[lmsMap[l]+1], nr = lms[lmsMap[r]+1];
            if (cmp(s[l..nl+1], s[r..nr+1])) recN++;
            recS[lmsMap[lms2[i]]] = recN;
        }

        induce(lms.indexed(sais!int(recS, recN)).array);
    }

    return sa;
}

SA!T suffixArray(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm;
    int n = _s.length.to!int;
    auto saInfo = SA!T(_s);
    if (n == 0) return saInfo;

    with (saInfo) {
        sa = sais(_s, B);

        sa.each!((i, v) => rsa[v] = i.to!int);

        int h = 0;
        foreach (i; 0..n) {
            int j = sa[rsa[i]-1];
            if (h > 0) h--;
            for (; j+h < n && i+h < n; h++) {
                if (s[j+h] != s[i+h]) break;
            }
            lcp[rsa[i]-1] = h;
        }
    }
    return saInfo;
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/scanner.d */
// module dcomp.scanner;

class Scanner {
    import std.stdio : File;
    import std.conv : to;
    import std.range : front, popFront, array, ElementType;
    import std.array : split;
    import std.traits : isSomeChar, isStaticArray, isArray;
    import std.algorithm : map;
    File f;
    this(File f) {
        this.f = f;
    }
    char[512] lineBuf;
    char[] line;
    private bool succ() {
        import std.range.primitives : empty, front, popFront;
        import std.ascii : isWhite;
        while (true) {
            while (!line.empty && line.front.isWhite) {
                line.popFront;
            }
            if (!line.empty) break;
            if (f.eof) return false;
            line = lineBuf[];
            f.readln(line);
        }
        return true;
    }

    private bool readSingle(T)(ref T x) {
        import std.algorithm : findSplitBefore;
        import std.string : strip;
        import std.conv : parse;
        if (!succ()) return false;
        static if (isArray!T) {
            alias E = ElementType!T;
            static if (isSomeChar!E) {

                auto r = line.findSplitBefore(" ");
                x = r[0].strip.dup;
                line = r[1];
            } else {
                auto buf = line.split.map!(to!E).array;
                static if (isStaticArray!T) {

                    assert(buf.length == T.length);
                }
                x = buf;
                line.length = 0;
            }
        } else {
            x = line.parse!T;
        }
        return true;
    }
    int read(T, Args...)(ref T x, auto ref Args args) {
        if (!readSingle(x)) return 0;
        static if (args.length == 0) {
            return 1;
        } else {
            return 1 + read(args);
        }
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/algorithm.d */
// module dcomp.algorithm;

import std.range.primitives;
import std.traits : isFloatingPoint, isIntegral;

T binSearch(alias pred, T)(T l, T r) if (isIntegral!T) {
    while (r-l > 1) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

T binSearch(alias pred, T)(T l, T r, int cnt = 60) if (isFloatingPoint!T) {
    foreach (i; 0..cnt) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

E minimum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? a : b)(seed, range);
}

ElementType!Range minimum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return minimum!pred(range, e);
}

E maximum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? b : a)(seed, range);
}

ElementType!Range maximum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return maximum!pred(range, e);
}

Rotator!Range rotator(Range)(Range r) {
    return Rotator!Range(r);
}

struct Rotator(Range)
if (isForwardRange!Range && hasLength!Range) {
    size_t cnt;
    Range start, now;
    this(Range r) {
        cnt = 0;
        start = r.save;
        now = r.save;
    }
    this(this) {
        start = start.save;
        now = now.save;
    }
    @property bool empty() {
        return now.empty;
    }
    @property auto front() {
        assert(!now.empty);
        import std.range : take, chain;
        return chain(now, start.take(cnt));
    }
    @property Rotator!Range save() {
        return this;
    }
    void popFront() {
        cnt++;
        now.popFront;
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/ascii.d */
// module dcomp.ascii;

struct ASCIIString {
    string s;
    alias s this;
    this(string s) {
        this.s = s;
    }
    ref immutable(char) front() const {
        return s[0];
    }
    void popFront() {
        s = s[1..$];
    }
    ref immutable(char) back() const {
        return s[$-1];
    }
    void popBack() {
        s = s[0..$-1];
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/foundation.d */
// module dcomp.foundation;

static if (__VERSION__ <= 2070) {
    template fold(fun...) if (fun.length >= 1) {
        auto fold(R, S...)(R r, S seed) {
            import std.algorithm : reduce;
            static if (S.length < 2) {
                return reduce!fun(seed, r);
            } else {
                import std.typecons : tuple;
                return reduce!fun(tuple(seed), r);
            }
        }
    }

}
version (X86) static if (__VERSION__ < 2071) {
    import core.bitop : bsf, bsr, popcnt;
    int bsf(ulong v) {
        foreach (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int bsr(ulong v) {
        foreach_reverse (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int popcnt(ulong v) {
        int c = 0;
        foreach (i; 0..64) {
            if (v & (1UL << i)) c++;
        }
        return c;
    }
}

/+ dub.sdl:
    name "I"
    dependency "dcomp" version=">=0.6.0"
+/

import std.stdio, std.algorithm, std.range, std.conv;
// import dcomp.foundation, dcomp.scanner;

// import dcomp.algorithm;
// import dcomp.string;
// import dcomp.datastructure.lazyseg;

void solve() {
    string s;
    sc.read(s);
    auto saInfo = suffixArray(s);
    int n = s.length.to!int;
    auto tr = LazySeg!(long, long, (a, b)=>a+b, (a, b)=>(b==-1)?a:b, (a, b)=>(b==-1)?a:b, 0, -1)(n);
    tr[0..n] += 10^^9;
    long sm = 0;
    foreach (i; 1..n) {
        auto u = saInfo.lcp[i];
        auto le = binSearch!(x => tr[x..x+1].sum >= u)(-1, i);
        tr[le..i] += u;
        sm += tr[0..i].sum;
//        writeln(tr);
    }
    writeln(sm*2 + long(n)*(n+1)/2);
}

int main() {
    int n;
    sc.read(n);
    foreach (i; 0..n) {
        solve();
    }
    return 0;
}

Scanner sc;
static this() {
    sc = new Scanner(stdin);
}
/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/datastructure/lazyseg.d */
// module dcomp.datastructure.lazyseg;

struct LazySeg(T, L, alias opTT, alias opTL, alias opLL, T eT, L eL) {
    const int n, sz;
    T[] d;
    L[] lz;
    @disable this();
    this(int n) {
        import std.algorithm : fill;
        import core.bitop : bsr;
        if (n == 0) return;
        int lg = n.bsr;
        if ((2^^lg) < n) lg++;
        this.n = n;
        this.sz = 2^^lg;
        d = new T[](2*this.sz); d[] = eT;
        lz = new L[](2*this.sz); lz[] = eL;
    }
    private void lzAdd(int k, L x) {
        d[k] = opTL(d[k], x);
        lz[k] = opLL(lz[k], x);
    }
    private void push(int k) {
        if (lz[k] == eL) return;
        lzAdd(2*k, lz[k]);
        lzAdd(2*k+1, lz[k]);
        lz[k] = eL;
    }
    T sum(int a, int b, int l, int r, int k) {
        if (b <= l || r <= a) return eT;
        if (a <= l && r <= b) return d[k];
        push(k);
        int md = (l+r)/2;
        return opTT(sum(a, b, l, md, 2*k),
            sum(a, b, md, r, 2*k+1));
    }
    T sum(int a, int b) {
        assert(0 <= a && a <= b && b <= n);
        return sum(a, b, 0, sz, 1);
    }
    void add(int a, int b, L x, int l, int r, int k) {
        if (b <= l || r <= a) return;
        if (a <= l && r <= b) {
            lzAdd(k, x);
            return;
        }
        push(k);
        int md = (l+r)/2;
        add(a, b, x, l, md, 2*k);
        add(a, b, x, md, r, 2*k+1);
        d[k] = opTT(d[2*k], d[2*k+1]);
    }
    void add(int a, int b, L x) {
        assert(0 <= a && a <= b && b <= n);
        add(a, b, x, 0, sz, 1);
    }
    @property int opDollar() const {return sz;}
    struct Range {
        LazySeg* seg;
        int start, end;
        @property T sum() {
            return seg.sum(start, end);
        }
    }
    int[2] opSlice(size_t dim)(int start, int end) {
        assert(0 <= start && start <= end && end <= sz);
        return [start, end];
    }
    Range opIndex(int[2] rng) {
        return Range(&this, rng[0], rng[1]);
    }
    void opIndexOpAssign(string op)(L x, int[2] rng) {
        add(rng[0], rng[1], x);
    }
}
/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/string.d */
// module dcomp.string;

struct SA(T) {
    T[] s;

    int[] sa, rsa, lcp;
    this(in T[] s) {
        size_t n = s.length;
        this.s = s.dup;
        sa = new int[](n+1);
        rsa = new int[](n+1);
        lcp = new int[](n);
    }
}

int[] sais(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm, std.range;
    int n = _s.length.to!int;
    int[] sa = new int[](n+1);
    if (n == 0) return sa;

    auto s = _s.map!"a+1".array ~ T(0); B++;

    bool[] ls = new bool[](n+1);
    ls[n] = true;
    foreach_reverse (i; 0..n) {
        ls[i] = (s[i] == s[i+1]) ? ls[i+1] : (s[i] < s[i+1]);
    }

    int[] sumL = new int[](B+1), sumS = new int[](B+1);
    s.each!((i, c) => !ls[i] ? sumS[c]++ : sumL[c+1]++);
    foreach (i; 0..B) {
        sumL[i+1] += sumS[i];
        sumS[i+1] += sumL[i+1];
    }

    void induce(in int[] lms) {
        sa[] = -1;
        auto buf0 = sumS.dup;
        foreach (d; lms) {
            sa[buf0[s[d]]++] = d;
        }
        auto buf1 = sumL.dup;
        foreach (v; sa) {
            if (v >= 1 && !ls[v-1]) {
                sa[buf1[s[v-1]]++] = v-1;
            }
        }
        auto buf2 = sumL.dup;
        foreach_reverse (v; sa) {
            if (v >= 1 && ls[v-1]) {
                sa[--buf2[s[v-1]+1]] = v-1;
            }
        }
    }

    int[] lms = iota(1, n+1).filter!(i => !ls[i-1] && ls[i]).array;
    int[] lmsMap = new int[](n+1);
    lmsMap[] = -1; lms.each!((i, v) => lmsMap[v] = i.to!int);

    induce(lms);

    if (lms.length >= 2) {
        int m = lms.length.to!int - 1;

        auto lms2 = sa.filter!(v => lmsMap[v] != -1).array;
        int recN = 1;
        int[] recS = new int[](m);
        recS[lmsMap[lms2[1]]] = 1;
        foreach (i; 2..m+1) {
            int l = lms2[i-1], r = lms2[i];
            int nl = lms[lmsMap[l]+1], nr = lms[lmsMap[r]+1];
            if (cmp(s[l..nl+1], s[r..nr+1])) recN++;
            recS[lmsMap[lms2[i]]] = recN;
        }

        induce(lms.indexed(sais!int(recS, recN)).array);
    }

    return sa;
}

SA!T suffixArray(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm;
    int n = _s.length.to!int;
    auto saInfo = SA!T(_s);
    if (n == 0) return saInfo;

    with (saInfo) {
        sa = sais(_s, B);

        sa.each!((i, v) => rsa[v] = i.to!int);

        int h = 0;
        foreach (i; 0..n) {
            int j = sa[rsa[i]-1];
            if (h > 0) h--;
            for (; j+h < n && i+h < n; h++) {
                if (s[j+h] != s[i+h]) break;
            }
            lcp[rsa[i]-1] = h;
        }
    }
    return saInfo;
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/scanner.d */
// module dcomp.scanner;

class Scanner {
    import std.stdio : File;
    import std.conv : to;
    import std.range : front, popFront, array, ElementType;
    import std.array : split;
    import std.traits : isSomeChar, isStaticArray, isArray;
    import std.algorithm : map;
    File f;
    this(File f) {
        this.f = f;
    }
    char[512] lineBuf;
    char[] line;
    private bool succ() {
        import std.range.primitives : empty, front, popFront;
        import std.ascii : isWhite;
        while (true) {
            while (!line.empty && line.front.isWhite) {
                line.popFront;
            }
            if (!line.empty) break;
            if (f.eof) return false;
            line = lineBuf[];
            f.readln(line);
        }
        return true;
    }

    private bool readSingle(T)(ref T x) {
        import std.algorithm : findSplitBefore;
        import std.string : strip;
        import std.conv : parse;
        if (!succ()) return false;
        static if (isArray!T) {
            alias E = ElementType!T;
            static if (isSomeChar!E) {

                auto r = line.findSplitBefore(" ");
                x = r[0].strip.dup;
                line = r[1];
            } else {
                auto buf = line.split.map!(to!E).array;
                static if (isStaticArray!T) {

                    assert(buf.length == T.length);
                }
                x = buf;
                line.length = 0;
            }
        } else {
            x = line.parse!T;
        }
        return true;
    }
    int read(T, Args...)(ref T x, auto ref Args args) {
        if (!readSingle(x)) return 0;
        static if (args.length == 0) {
            return 1;
        } else {
            return 1 + read(args);
        }
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/ascii.d */
// module dcomp.ascii;

struct ASCIIString {
    string s;
    alias s this;
    this(string s) {
        this.s = s;
    }
    ref immutable(char) front() const {
        return s[0];
    }
    void popFront() {
        s = s[1..$];
    }
    ref immutable(char) back() const {
        return s[$-1];
    }
    void popBack() {
        s = s[0..$-1];
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/algorithm.d */
// module dcomp.algorithm;

import std.range.primitives;
import std.traits : isFloatingPoint, isIntegral;

T binSearch(alias pred, T)(T l, T r) if (isIntegral!T) {
    while (r-l > 1) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

T binSearch(alias pred, T)(T l, T r, int cnt = 60) if (isFloatingPoint!T) {
    foreach (i; 0..cnt) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

E minimum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? a : b)(seed, range);
}

ElementType!Range minimum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return minimum!pred(range, e);
}

E maximum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? b : a)(seed, range);
}

ElementType!Range maximum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return maximum!pred(range, e);
}

Rotator!Range rotator(Range)(Range r) {
    return Rotator!Range(r);
}

struct Rotator(Range)
if (isForwardRange!Range && hasLength!Range) {
    size_t cnt;
    Range start, now;
    this(Range r) {
        cnt = 0;
        start = r.save;
        now = r.save;
    }
    this(this) {
        start = start.save;
        now = now.save;
    }
    @property bool empty() {
        return now.empty;
    }
    @property auto front() {
        assert(!now.empty);
        import std.range : take, chain;
        return chain(now, start.take(cnt));
    }
    @property Rotator!Range save() {
        return this;
    }
    void popFront() {
        cnt++;
        now.popFront;
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/foundation.d */
// module dcomp.foundation;

static if (__VERSION__ <= 2070) {
    template fold(fun...) if (fun.length >= 1) {
        auto fold(R, S...)(R r, S seed) {
            import std.algorithm : reduce;
            static if (S.length < 2) {
                return reduce!fun(seed, r);
            } else {
                import std.typecons : tuple;
                return reduce!fun(tuple(seed), r);
            }
        }
    }

}
version (X86) static if (__VERSION__ < 2071) {
    int bsf(ulong v) {
        foreach (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int bsr(ulong v) {
        foreach_reverse (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int popcnt(ulong v) {
        int c = 0;
        foreach (i; 0..64) {
            if (v & (1UL << i)) c++;
        }
        return c;
    }
}

/+ dub.sdl:
    name "I"
    dependency "dcomp" version=">=0.6.0"
+/

import std.stdio, std.algorithm, std.range, std.conv;
// import dcomp.foundation, dcomp.scanner;

// import dcomp.algorithm;
// import dcomp.string;
// import dcomp.datastructure.lazyseg;

void solve() {
    string s;
    sc.read(s);
    auto saInfo = suffixArray(s);
    int n = s.length.to!int;
    auto tr = LazySeg!(int, int, (a, b)=>a+b, (a, b)=>(b==-1)?a:b, (a, b)=>(b==-1)?a:b, 0, -1)(n);
    tr[0..n] += 10^^9;
    long sm = 0;
    foreach (i; 1..n) {
        auto u = saInfo.lcp[i];
        auto le = binSearch!(x => tr[x..x+1].sum >= u)(-1, i);
        tr[le..i] += u;
        sm += tr[0..i].sum;
//        writeln(tr);
    }
    writeln(sm*2 + long(n)*(n+1)/2);
}

int main() {
    int n;
    sc.read(n);
    foreach (i; 0..n) {
        solve();
    }
    return 0;
}

Scanner sc;
static this() {
    sc = new Scanner(stdin);
}
/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/datastructure/lazyseg.d */
// module dcomp.datastructure.lazyseg;

struct LazySeg(T, L, alias opTT, alias opTL, alias opLL, T eT, L eL) {
    const int n, sz;
    T[] d;
    L[] lz;
    @disable this();
    this(int n) {
        import std.algorithm : fill;
        import core.bitop : bsr;
        if (n == 0) return;
        int lg = n.bsr;
        if ((2^^lg) < n) lg++;
        this.n = n;
        this.sz = 2^^lg;
        d = new T[](2*this.sz); d[] = eT;
        lz = new L[](2*this.sz); lz[] = eL;
    }
    private void lzAdd(int k, L x) {
        d[k] = opTL(d[k], x);
        lz[k] = opLL(lz[k], x);
    }
    private void push(int k) {
        if (lz[k] == eL) return;
        lzAdd(2*k, lz[k]);
        lzAdd(2*k+1, lz[k]);
        lz[k] = eL;
    }
    T sum(int a, int b, int l, int r, int k) {
        if (b <= l || r <= a) return eT;
        if (a <= l && r <= b) return d[k];
        push(k);
        int md = (l+r)/2;
        return opTT(sum(a, b, l, md, 2*k),
            sum(a, b, md, r, 2*k+1));
    }
    T sum(int a, int b) {
        assert(0 <= a && a <= b && b <= n);
        return sum(a, b, 0, sz, 1);
    }
    void add(int a, int b, L x, int l, int r, int k) {
        if (b <= l || r <= a) return;
        if (a <= l && r <= b) {
            lzAdd(k, x);
            return;
        }
        push(k);
        int md = (l+r)/2;
        add(a, b, x, l, md, 2*k);
        add(a, b, x, md, r, 2*k+1);
        d[k] = opTT(d[2*k], d[2*k+1]);
    }
    void add(int a, int b, L x) {
        assert(0 <= a && a <= b && b <= n);
        add(a, b, x, 0, sz, 1);
    }
    @property int opDollar() const {return sz;}
    struct Range {
        LazySeg* seg;
        int start, end;
        @property T sum() {
            return seg.sum(start, end);
        }
    }
    int[2] opSlice(size_t dim)(int start, int end) {
        assert(0 <= start && start <= end && end <= sz);
        return [start, end];
    }
    Range opIndex(int[2] rng) {
        return Range(&this, rng[0], rng[1]);
    }
    void opIndexOpAssign(string op)(L x, int[2] rng) {
        add(rng[0], rng[1], x);
    }
}
/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/string.d */
// module dcomp.string;

struct SA(T) {
    T[] s;

    int[] sa, rsa, lcp;
    this(in T[] s) {
        size_t n = s.length;
        this.s = s.dup;
        sa = new int[](n+1);
        rsa = new int[](n+1);
        lcp = new int[](n);
    }
}

int[] sais(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm, std.range;
    int n = _s.length.to!int;
    int[] sa = new int[](n+1);
    if (n == 0) return sa;

    auto s = _s.map!"a+1".array ~ T(0); B++;

    bool[] ls = new bool[](n+1);
    ls[n] = true;
    foreach_reverse (i; 0..n) {
        ls[i] = (s[i] == s[i+1]) ? ls[i+1] : (s[i] < s[i+1]);
    }

    int[] sumL = new int[](B+1), sumS = new int[](B+1);
    s.each!((i, c) => !ls[i] ? sumS[c]++ : sumL[c+1]++);
    foreach (i; 0..B) {
        sumL[i+1] += sumS[i];
        sumS[i+1] += sumL[i+1];
    }

    void induce(in int[] lms) {
        sa[] = -1;
        auto buf0 = sumS.dup;
        foreach (d; lms) {
            sa[buf0[s[d]]++] = d;
        }
        auto buf1 = sumL.dup;
        foreach (v; sa) {
            if (v >= 1 && !ls[v-1]) {
                sa[buf1[s[v-1]]++] = v-1;
            }
        }
        auto buf2 = sumL.dup;
        foreach_reverse (v; sa) {
            if (v >= 1 && ls[v-1]) {
                sa[--buf2[s[v-1]+1]] = v-1;
            }
        }
    }

    int[] lms = iota(1, n+1).filter!(i => !ls[i-1] && ls[i]).array;
    int[] lmsMap = new int[](n+1);
    lmsMap[] = -1; lms.each!((i, v) => lmsMap[v] = i.to!int);

    induce(lms);

    if (lms.length >= 2) {
        int m = lms.length.to!int - 1;

        auto lms2 = sa.filter!(v => lmsMap[v] != -1).array;
        int recN = 1;
        int[] recS = new int[](m);
        recS[lmsMap[lms2[1]]] = 1;
        foreach (i; 2..m+1) {
            int l = lms2[i-1], r = lms2[i];
            int nl = lms[lmsMap[l]+1], nr = lms[lmsMap[r]+1];
            if (cmp(s[l..nl+1], s[r..nr+1])) recN++;
            recS[lmsMap[lms2[i]]] = recN;
        }

        induce(lms.indexed(sais!int(recS, recN)).array);
    }

    return sa;
}

SA!T suffixArray(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm;
    int n = _s.length.to!int;
    auto saInfo = SA!T(_s);
    if (n == 0) return saInfo;

    with (saInfo) {
        sa = sais(_s, B);

        sa.each!((i, v) => rsa[v] = i.to!int);

        int h = 0;
        foreach (i; 0..n) {
            int j = sa[rsa[i]-1];
            if (h > 0) h--;
            for (; j+h < n && i+h < n; h++) {
                if (s[j+h] != s[i+h]) break;
            }
            lcp[rsa[i]-1] = h;
        }
    }
    return saInfo;
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/scanner.d */
// module dcomp.scanner;

class Scanner {
    import std.stdio : File;
    import std.conv : to;
    import std.range : front, popFront, array, ElementType;
    import std.array : split;
    import std.traits : isSomeChar, isStaticArray, isArray;
    import std.algorithm : map;
    File f;
    this(File f) {
        this.f = f;
    }
    char[512] lineBuf;
    char[] line;
    private bool succ() {
        import std.range.primitives : empty, front, popFront;
        import std.ascii : isWhite;
        while (true) {
            while (!line.empty && line.front.isWhite) {
                line.popFront;
            }
            if (!line.empty) break;
            if (f.eof) return false;
            line = lineBuf[];
            f.readln(line);
        }
        return true;
    }

    private bool readSingle(T)(ref T x) {
        import std.algorithm : findSplitBefore;
        import std.string : strip;
        import std.conv : parse;
        if (!succ()) return false;
        static if (isArray!T) {
            alias E = ElementType!T;
            static if (isSomeChar!E) {

                auto r = line.findSplitBefore(" ");
                x = r[0].strip.dup;
                line = r[1];
            } else {
                auto buf = line.split.map!(to!E).array;
                static if (isStaticArray!T) {

                    assert(buf.length == T.length);
                }
                x = buf;
                line.length = 0;
            }
        } else {
            x = line.parse!T;
        }
        return true;
    }
    int read(T, Args...)(ref T x, auto ref Args args) {
        if (!readSingle(x)) return 0;
        static if (args.length == 0) {
            return 1;
        } else {
            return 1 + read(args);
        }
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/ascii.d */
// module dcomp.ascii;

struct ASCIIString {
    string s;
    alias s this;
    this(string s) {
        this.s = s;
    }
    ref immutable(char) front() const {
        return s[0];
    }
    void popFront() {
        s = s[1..$];
    }
    ref immutable(char) back() const {
        return s[$-1];
    }
    void popBack() {
        s = s[0..$-1];
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/algorithm.d */
// module dcomp.algorithm;

import std.range.primitives;
import std.traits : isFloatingPoint, isIntegral;

T binSearch(alias pred, T)(T l, T r) if (isIntegral!T) {
    while (r-l > 1) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

T binSearch(alias pred, T)(T l, T r, int cnt = 60) if (isFloatingPoint!T) {
    foreach (i; 0..cnt) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

E minimum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? a : b)(seed, range);
}

ElementType!Range minimum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return minimum!pred(range, e);
}

E maximum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? b : a)(seed, range);
}

ElementType!Range maximum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return maximum!pred(range, e);
}

Rotator!Range rotator(Range)(Range r) {
    return Rotator!Range(r);
}

struct Rotator(Range)
if (isForwardRange!Range && hasLength!Range) {
    size_t cnt;
    Range start, now;
    this(Range r) {
        cnt = 0;
        start = r.save;
        now = r.save;
    }
    this(this) {
        start = start.save;
        now = now.save;
    }
    @property bool empty() {
        return now.empty;
    }
    @property auto front() {
        assert(!now.empty);
        import std.range : take, chain;
        return chain(now, start.take(cnt));
    }
    @property Rotator!Range save() {
        return this;
    }
    void popFront() {
        cnt++;
        now.popFront;
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/foundation.d */
// module dcomp.foundation;

static if (__VERSION__ <= 2070) {
    template fold(fun...) if (fun.length >= 1) {
        auto fold(R, S...)(R r, S seed) {
            import std.algorithm : reduce;
            static if (S.length < 2) {
                return reduce!fun(seed, r);
            } else {
                import std.typecons : tuple;
                return reduce!fun(tuple(seed), r);
            }
        }
    }

}
version (X86) static if (__VERSION__ < 2071) {
    int bsf(ulong v) {
        foreach (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int bsr(ulong v) {
        foreach_reverse (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int popcnt(ulong v) {
        int c = 0;
        foreach (i; 0..64) {
            if (v & (1UL << i)) c++;
        }
        return c;
    }
}

/+ dub.sdl:
    name "I"
    dependency "dcomp" version=">=0.6.0"
+/

import std.stdio, std.algorithm, std.range, std.conv, std.traits;
// import dcomp.foundation, dcomp.scanner;
// import dcomp.array;
// import dcomp.algorithm;
// import dcomp.string;

/// 遅延伝搬Segment Tree
struct LazySeg(T, L, alias opTT, alias opTL, alias opLL, T eT, L eL) {
    const int n, sz, lg;
    T[] d;
    L[] lz;
    @disable this();
    this(int n) {
        import std.algorithm : fill, each;
        import core.bitop : bsr;
        if (n == 0) return;
        int lg = n.bsr;
        if ((2^^lg) < n) lg++;
        this.n = n;
        this.sz = 2^^lg;
        this.lg = lg;
        d = new T[](2*this.sz);
        d.each!((ref x) => x = eT);
        lz = new L[](2*this.sz);
        lz.each!((ref x) => x = eL);
    }
    private void lzAdd(int k, L x) {
        d[k] = opTL(d[k], x);
        lz[k] = opLL(lz[k], x);
    }
    private void push(int k) {
        if (lz[k] == eL) return;
        lzAdd(2*k, lz[k]);
        lzAdd(2*k+1, lz[k]);
        lz[k] = eL;
    }
    //d[a]+d[a+1]+...+d[b-1]
    T sum(int a, int b, int l, int r, int k) {
        if (b <= l || r <= a) return eT;
        if (a <= l && r <= b) return d[k];
        push(k);
        int md = (l+r)/2;
        return opTT(sum(a, b, l, md, 2*k),
            sum(a, b, md, r, 2*k+1));
    }
    T single(int k) {
        k += sz;
        foreach_reverse (int i; 1..lg+1) {
            push(k>>i);
        }
        return d[k];
    }
    void singleSet(T x, int k) {
        k += sz;
        foreach_reverse (int i; 1..lg+1) {
            push(k>>i);
        }
        d[k] = x;
        foreach (int i; 1..lg+1) {
            d[k>>i] = opTT(d[2*(k>>i)], d[2*(k>>i)+1]);
        }
    }
    T sum(int a, int b) {
        assert(0 <= a && a <= b && b <= n);
        return sum(a, b, 0, sz, 1);
    }
    void add(int a, int b, L x, int l, int r, int k) {
        if (b <= l || r <= a) return;
        if (a <= l && r <= b) {
            lzAdd(k, x);
            return;
        }
        push(k);
        int md = (l+r)/2;
        add(a, b, x, l, md, 2*k);
        add(a, b, x, md, r, 2*k+1);
        d[k] = opTT(d[2*k], d[2*k+1]);
    }
    void add(int a, int b, L x) {
        assert(0 <= a && a <= b && b <= n);
        add(a, b, x, 0, sz, 1);
    }
    @property int opDollar() const {return sz;}
    struct Range {
        LazySeg* seg;
        int start, end;
        @property T sum() {
            return seg.sum(start, end);
        }
    }
    T opIndex(int k) {
        assert(0 <= k && k < n);
        return single(k);
    }
    void opIndexAssign(T x, int k) {
        assert(0 <= k && k < n);
        singleSet(x, k);
    }
    int[2] opSlice(size_t dim)(int start, int end) {
        assert(0 <= start && start <= end && end <= sz);
        return [start, end];
    }
    Range opIndex(int[2] rng) {
        return Range(&this, rng[0], rng[1]);
    }
    void opIndexOpAssign(string op : "+")(L x, int[2] rng) {
        add(rng[0], rng[1], x);
    }
}

int binSearchLeft(alias pred, TR)(TR t, int a, int b)
if (isInstanceOf!(LazySeg, TR)) {
    alias args = TemplateArgsOf!TR;
    alias opTT = args[2];
    with (t) {
        auto x = args[5];
        if (pred(x)) return a-1;
        int pos = a;
        void f(int a, int b, int l, int r, int k) {
            if (b <= l || r <= a) return;
            if (a <= l && r <= b && !pred(opTT(x, d[k]))) {
                x = opTT(x, d[k]);
                pos = r;
                return;
            }
            if (l+1 == r) return;
            push(k);
            int md = (l+r)/2;
            f(a, b, l, md, 2*k);
            if (pos >= md) f(a, b, md, r, 2*k+1);
        }
        f(a, b, 0, sz, 1);
        return pos;
    }
}

void solve() {
    string s;
    sc.read(s);
    auto saInfo = suffixArray(s);
    int n = s.length.to!int;
    import std.typecons;
    alias T = Tuple!(long, int, int);
    auto tr = LazySeg!(T, int,
        (a, b)=>T(a[0]+b[0], a[1]+b[1], max(a[2], b[2])),
        (a, b)=>T(b * a[1], a[1], b),
        (a, b)=>b,
        T(0L, 1, -(10^^9)), -1)(n);
    tr[0..n] += 10^^9;
    long sm = 0;
    foreach (i; 1..n) {
        auto u = saInfo.lcp[i];
        auto le = tr.binSearchLeft!(x => x[2] >= u)(0, i);
        tr[le..i] += u;
        sm += tr[0..i].sum[0];
//        writeln(tr);
    }
    writeln(sm*2 + long(n)*(n+1)/2);
}

int main() {
    int n;
    sc.read(n);
    foreach (i; 0..n) {
        solve();
    }
    return 0;
}

Scanner sc;
static this() {
    sc = new Scanner(stdin);
}
/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/array.d */
// module dcomp.array;

T[N] fixed(T, size_t N)(T[N] a) {return a;}

struct FastAppender(A) {
    import std.algorithm : max;
    import std.range.primitives : ElementEncodingType;
    import core.stdc.string : memcpy;

    private alias T = ElementEncodingType!A;
    private T* _data;
    private size_t len, cap;

    @property size_t length() {return len;}

    void reserve(size_t nlen) {
        import core.memory : GC;
        if (nlen <= cap) return;

        void* nx = GC.malloc(nlen * T.sizeof);

        cap = nlen;
        if (len) memcpy(nx, _data, len * T.sizeof);
        _data = cast(T*)(nx);
    }

    void opOpAssign(string op : "~")(T item) {
        if (len == cap) {
            reserve(max(4, cap*2));
        }
        _data[len++] = item;
    }

    void clear() {
        len = 0;
    }

    T[] data() {
        return (_data) ? _data[0..len] : null;
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/string.d */
// module dcomp.string;

struct SA(T) {
    T[] s;

    int[] sa, rsa, lcp;
    this(in T[] s) {
        size_t n = s.length;
        this.s = s.dup;
        sa = new int[](n+1);
        rsa = new int[](n+1);
        lcp = new int[](n);
    }
}

int[] sais(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm, std.range;
    int n = _s.length.to!int;
    int[] sa = new int[](n+1);
    if (n == 0) return sa;

    auto s = _s.map!"a+1".array ~ T(0); B++;

    bool[] ls = new bool[](n+1);
    ls[n] = true;
    foreach_reverse (i; 0..n) {
        ls[i] = (s[i] == s[i+1]) ? ls[i+1] : (s[i] < s[i+1]);
    }

    int[] sumL = new int[](B+1), sumS = new int[](B+1);
    s.each!((i, c) => !ls[i] ? sumS[c]++ : sumL[c+1]++);
    foreach (i; 0..B) {
        sumL[i+1] += sumS[i];
        sumS[i+1] += sumL[i+1];
    }

    void induce(in int[] lms) {
        sa[] = -1;
        auto buf0 = sumS.dup;
        foreach (d; lms) {
            sa[buf0[s[d]]++] = d;
        }
        auto buf1 = sumL.dup;
        foreach (v; sa) {
            if (v >= 1 && !ls[v-1]) {
                sa[buf1[s[v-1]]++] = v-1;
            }
        }
        auto buf2 = sumL.dup;
        foreach_reverse (v; sa) {
            if (v >= 1 && ls[v-1]) {
                sa[--buf2[s[v-1]+1]] = v-1;
            }
        }
    }

    int[] lms = iota(1, n+1).filter!(i => !ls[i-1] && ls[i]).array;
    int[] lmsMap = new int[](n+1);
    lmsMap[] = -1; lms.each!((i, v) => lmsMap[v] = i.to!int);

    induce(lms);

    if (lms.length >= 2) {
        int m = lms.length.to!int - 1;

        auto lms2 = sa.filter!(v => lmsMap[v] != -1).array;
        int recN = 1;
        int[] recS = new int[](m);
        recS[lmsMap[lms2[1]]] = 1;
        foreach (i; 2..m+1) {
            int l = lms2[i-1], r = lms2[i];
            int nl = lms[lmsMap[l]+1], nr = lms[lmsMap[r]+1];
            if (cmp(s[l..nl+1], s[r..nr+1])) recN++;
            recS[lmsMap[lms2[i]]] = recN;
        }

        induce(lms.indexed(sais!int(recS, recN)).array);
    }

    return sa;
}

SA!T suffixArray(T)(in T[] _s, int B = 200) {
    import std.conv, std.algorithm;
    int n = _s.length.to!int;
    auto saInfo = SA!T(_s);
    if (n == 0) return saInfo;

    with (saInfo) {
        sa = sais(_s, B);

        sa.each!((i, v) => rsa[v] = i.to!int);

        int h = 0;
        foreach (i; 0..n) {
            int j = sa[rsa[i]-1];
            if (h > 0) h--;
            for (; j+h < n && i+h < n; h++) {
                if (s[j+h] != s[i+h]) break;
            }
            lcp[rsa[i]-1] = h;
        }
    }
    return saInfo;
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/scanner.d */
// module dcomp.scanner;

class Scanner {
    import std.stdio : File;
    import std.conv : to;
    import std.range : front, popFront, array, ElementType;
    import std.array : split;
    import std.traits : isSomeChar, isStaticArray, isArray;
    import std.algorithm : map;
    File f;
    this(File f) {
        this.f = f;
    }
    char[512] lineBuf;
    char[] line;
    private bool succ() {
        import std.range.primitives : empty, front, popFront;
        import std.ascii : isWhite;
        while (true) {
            while (!line.empty && line.front.isWhite) {
                line.popFront;
            }
            if (!line.empty) break;
            if (f.eof) return false;
            line = lineBuf[];
            f.readln(line);
        }
        return true;
    }

    private bool readSingle(T)(ref T x) {
        import std.algorithm : findSplitBefore;
        import std.string : strip;
        import std.conv : parse;
        if (!succ()) return false;
        static if (isArray!T) {
            alias E = ElementType!T;
            static if (isSomeChar!E) {

                auto r = line.findSplitBefore(" ");
                x = r[0].strip.dup;
                line = r[1];
            } else {
                auto buf = line.split.map!(to!E).array;
                static if (isStaticArray!T) {

                    assert(buf.length == T.length);
                }
                x = buf;
                line.length = 0;
            }
        } else {
            x = line.parse!T;
        }
        return true;
    }
    int read(T, Args...)(ref T x, auto ref Args args) {
        if (!readSingle(x)) return 0;
        static if (args.length == 0) {
            return 1;
        } else {
            return 1 + read(args);
        }
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/algorithm.d */
// module dcomp.algorithm;

import std.range.primitives;
import std.traits : isFloatingPoint, isIntegral;

T binSearch(alias pred, T)(T l, T r) if (isIntegral!T) {
    while (r-l > 1) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

T binSearch(alias pred, T)(T l, T r, int cnt = 60) if (isFloatingPoint!T) {
    foreach (i; 0..cnt) {
        T md = (l+r)/2;
        if (!pred(md)) l = md;
        else r = md;
    }
    return r;
}

E minimum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? a : b)(seed, range);
}

ElementType!Range minimum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return minimum!pred(range, e);
}

E maximum(alias pred = "a < b", Range, E = ElementType!Range)(Range range, E seed)
if (isInputRange!Range && !isInfinite!Range) {
    import std.algorithm, std.functional;
    return reduce!((a, b) => binaryFun!pred(a, b) ? b : a)(seed, range);
}

ElementType!Range maximum(alias pred = "a < b", Range)(Range range) {
    assert(!range.empty, "range must not empty");
    auto e = range.front; range.popFront;
    return maximum!pred(range, e);
}

Rotator!Range rotator(Range)(Range r) {
    return Rotator!Range(r);
}

struct Rotator(Range)
if (isForwardRange!Range && hasLength!Range) {
    size_t cnt;
    Range start, now;
    this(Range r) {
        cnt = 0;
        start = r.save;
        now = r.save;
    }
    this(this) {
        start = start.save;
        now = now.save;
    }
    @property bool empty() {
        return now.empty;
    }
    @property auto front() {
        assert(!now.empty);
        import std.range : take, chain;
        return chain(now, start.take(cnt));
    }
    @property Rotator!Range save() {
        return this;
    }
    void popFront() {
        cnt++;
        now.popFront;
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/ascii.d */
// module dcomp.ascii;

struct ASCIIString {
    string s;
    alias s this;
    this(string s) {
        this.s = s;
    }
    ref immutable(char) front() const {
        return s[0];
    }
    void popFront() {
        s = s[1..$];
    }
    ref immutable(char) back() const {
        return s[$-1];
    }
    void popBack() {
        s = s[0..$-1];
    }
}

/* IMPORT /Users/yosupo/Program/dcomp/source/dcomp/foundation.d */
// module dcomp.foundation;

static if (__VERSION__ <= 2070) {
    template fold(fun...) if (fun.length >= 1) {
        auto fold(R, S...)(R r, S seed) {
            import std.algorithm : reduce;
            static if (S.length < 2) {
                return reduce!fun(seed, r);
            } else {
                import std.typecons : tuple;
                return reduce!fun(tuple(seed), r);
            }
        }
    }

}
version (X86) static if (__VERSION__ < 2071) {
    import core.bitop : bsf, bsr, popcnt;
    int bsf(ulong v) {
        foreach (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int bsr(ulong v) {
        foreach_reverse (i; 0..64) {
            if (v & (1UL << i)) return i;
        }
        return -1;
    }
    int popcnt(ulong v) {
        int c = 0;
        foreach (i; 0..64) {
            if (v & (1UL << i)) c++;
        }
        return c;
    }
}


It's hard times now. Today Petya needs to score 100 points on Informatics exam. The tasks seem easy to Petya, but he thinks he lacks time to finish them all, so he asks you to help with one..There is a glob pattern in the statements (a string consisting of lowercase English letters, characters "?" and "*"). It is known that character "*" occurs no more than once in the pattern.Also, n query strings are given, it is required to determine for each of them if the pattern matches it or not.Everything seemed easy to Petya, but then he discovered that the special pattern characters differ from their usual meaning.A pattern matches a string if it is possible to replace each character "?" with one good lowercase English letter, and the character "*" (if there is one) with any, including empty, string of bad lowercase English letters, so that the resulting string is the same as the given string.The good letters are given to Petya. All the others are bad.

The first line contains a string with length from 1 to 26 consisting of distinct lowercase English letters. These letters are good letters, all the others are bad. The second line contains the pattern — a string s of lowercase English letters, characters "?" and "*" (1 ≤ |s| ≤ 105). It is guaranteed that character "*" occurs in s no more than once. The third line contains integer n (1 ≤ n ≤ 105) — the number of query strings. n lines follow, each of them contains single non-empty string consisting of lowercase English letters — a query string. It is guaranteed that the total length of all query strings is not greater than 105.

Print n lines: in the i-th of them print "YES" if the pattern matches the i-th query string, and "NO" otherwise. You can choose the case (lower or upper) for each letter arbitrary.

NoteIn the first example we can replace "?" with good letters "a" and "b", so we can see that the answer for the first query is "YES", and the answer for the second query is "NO", because we can't match the third letter.Explanation of the second example.   The first query: "NO", because character "*" can be replaced with a string of bad letters only, but the only way to match the query string is to replace it with the string "ba", in which both letters are good.  The second query: "YES", because characters "?" can be replaced with corresponding good letters, and character "*" can be replaced with empty string, and the strings will coincide.  The third query: "NO", because characters "?" can't be replaced with bad letters.  The fourth query: "YES", because characters "?" can be replaced with good letters "a", and character "*" can be replaced with a string of bad letters "x".

// tested by Hightail - https://github.com/dj3500/hightail
import std.stdio, std.string, std.conv, std.algorithm;
import std.range, std.array, std.math, std.typecons, std.container, core.bitop;
import std.datetime, std.bigint;

bool[] ok;
bool flag;

void main() {
    string oks = readln.chomp;
    ok = new bool[](26);
    foreach (ch ; oks) {
        ok[ch - 'a'] = true;
    }
    string pat = readln.chomp;

    foreach (ch ; pat) {
        if (ch == '*') {
            flag = true;
        }
    }

    int n = readln.chomp.to!int;

    while (n--) {
        string gs = readln.chomp;
        writeln(check(pat, gs) ? "YES" : "NO");
    }
}

bool check(string pat, string gs) {
    while (!pat.empty && pat.front != '*') {
        if (pat.front == '?' && !ok[gs.front - 'a']) {
            return false;
        }
        if (pat.front != '?' && (pat.front != gs.front)) {
            return false;
        }

        pat.popFront();
        gs.popFront();
    }

    while (!pat.empty && pat.back != '*') {
        if (pat.back == '?' && !ok[gs.back - 'a']) {
            return false;
        }
        if (pat.back != '?' && (pat.back != gs.back)) {
            return false;
        }

        pat.popBack();
        gs.popBack();
    }

    debug {
        writeln("gs:", gs);
    }

    if (!flag && !gs.empty) {
        return false;
    }

    foreach (ch ; gs) {
        if (ok[ch - 'a']) {
            return false;
        }
    }

    return true;
}

void scan(T...)(ref T args) {
    string[] line = readln.split;
    foreach (ref arg; args) {
        arg = line.front.to!(typeof(arg));
        line.popFront();
    }
    assert(line.empty);
}

void fillAll(R, T)(ref R arr, T value) {
    static if (is(typeof(arr[] = value))) {
        arr[] = value;
    }
    else {
        foreach (ref e; arr) {
            fillAll(e, value);
        }
    }
}

// tested by Hightail - https://github.com/dj3500/hightail
import std.stdio, std.string, std.conv, std.algorithm;
import std.range, std.array, std.math, std.typecons, std.container, core.bitop;
import std.datetime, std.bigint;

bool[] ok;

void main() {
    string oks = readln.chomp;
    ok = new bool[](26);
    foreach (ch ; oks) {
        ok[ch - 'a'] = true;
    }
    string pat = readln.chomp;

    int n = readln.chomp.to!int;

    while (n--) {
        string gs = readln.chomp;
        writeln(check(pat, gs) ? "YES" : "NO");
    }
}

bool check(string pat, string gs) {
    while (!pat.empty && pat.front != '*') {
        if (pat.front == '?' && !ok[gs.front - 'a']) {
            return false;
        }
        if (pat.front != '?' && (pat.front != gs.front)) {
            return false;
        }

        pat.popFront();
        gs.popFront();
    }

    while (!pat.empty && pat.back != '*') {
        if (pat.back == '?' && !ok[gs.back - 'a']) {
            return false;
        }
        if (pat.back != '?' && (pat.back != gs.back)) {
            return false;
        }

        pat.popBack();
        gs.popBack();
    }

    debug {
        writeln("gs:", gs);
    }

    foreach (ch ; gs) {
        if (ok[ch - 'a']) {
            return false;
        }
    }

    return true;
}

void scan(T...)(ref T args) {
    string[] line = readln.split;
    foreach (ref arg; args) {
        arg = line.front.to!(typeof(arg));
        line.popFront();
    }
    assert(line.empty);
}

void fillAll(R, T)(ref R arr, T value) {
    static if (is(typeof(arr[] = value))) {
        arr[] = value;
    }
    else {
        foreach (ref e; arr) {
            fillAll(e, value);
        }
    }
}


In the $$$2022$$$ year, Mike found two binary integers $$$a$$$ and $$$b$$$ of length $$$n$$$ (both of them are written only by digits $$$0$$$ and $$$1$$$) that can have leading zeroes. In order not to forget them, he wanted to construct integer $$$d$$$ in the following way:   he creates an integer $$$c$$$ as a result of bitwise summing of $$$a$$$ and $$$b$$$ without transferring carry, so $$$c$$$ may have one or more $$$2$$$-s. For example, the result of bitwise summing of $$$0110$$$ and $$$1101$$$ is $$$1211$$$ or the sum of $$$011000$$$ and $$$011000$$$ is $$$022000$$$;  after that Mike replaces equal consecutive digits in $$$c$$$ by one digit, thus getting $$$d$$$. In the cases above after this operation, $$$1211$$$ becomes $$$121$$$ and $$$022000$$$ becomes $$$020$$$ (so, $$$d$$$ won't have equal consecutive digits). Unfortunately, Mike lost integer $$$a$$$ before he could calculate $$$d$$$ himself. Now, to cheer him up, you want to find any binary integer $$$a$$$ of length $$$n$$$ such that $$$d$$$ will be maximum possible as integer.Maximum possible as integer means that $$$102 > 21$$$, $$$012 < 101$$$, $$$021 = 21$$$ and so on.

The first line contains a single integer $$$t$$$ ($$$1 \leq t \leq 1000$$$) — the number of test cases. The first line of each test case contains the integer $$$n$$$ ($$$1 \leq n \leq 10^5$$$) — the length of $$$a$$$ and $$$b$$$. The second line of each test case contains binary integer $$$b$$$ of length $$$n$$$. The integer $$$b$$$ consists only of digits $$$0$$$ and $$$1$$$. It is guaranteed that the total sum of $$$n$$$ over all $$$t$$$ test cases doesn't exceed $$$10^5$$$.

For each test case output one binary integer $$$a$$$ of length $$$n$$$. Note, that $$$a$$$ or $$$b$$$ may have leading zeroes but must have the same length $$$n$$$.

NoteIn the first test case, $$$b = 0$$$ and choosing $$$a = 1$$$ gives $$$d = 1$$$ as a result.In the second test case, $$$b = 011$$$ so:   if you choose $$$a = 000$$$, $$$c$$$ will be equal to $$$011$$$, so $$$d = 01$$$;  if you choose $$$a = 111$$$, $$$c$$$ will be equal to $$$122$$$, so $$$d = 12$$$;  if you choose $$$a = 010$$$, you'll get $$$d = 021$$$.  If you select $$$a = 110$$$, you'll get $$$d = 121$$$.  We can show that answer $$$a = 110$$$ is optimal and $$$d = 121$$$ is maximum possible.In the third test case, $$$b = 110$$$. If you choose $$$a = 100$$$, you'll get $$$d = 210$$$ and it's the maximum possible $$$d$$$.In the fourth test case, $$$b = 111000$$$. If you choose $$$a = 101101$$$, you'll get $$$d = 212101$$$ and it's maximum possible $$$d$$$.In the fifth test case, $$$b = 001011$$$. If you choose $$$a = 101110$$$, you'll get $$$d = 102121$$$ and it's maximum possible $$$d$$$.

import std.stdio, std.algorithm, std.conv, std.array, std.string, std.math, std.typecons, std.numeric, std.container, std.range;

void get(Args...)(ref Args args)
{
    import std.traits, std.meta, std.typecons;

    static if (Args.length == 1) {
        alias Arg = Args[0];

        static if (isArray!Arg) {
          static if (isSomeChar!(ElementType!Arg)) {
            args[0] = readln.chomp.to!Arg;
          } else {
            args[0] = readln.split.to!Arg;
          }
        } else static if (isTuple!Arg) {
            auto input = readln.split;
            static foreach (i; 0..Fields!Arg.length) {
                args[0][i] = input[i].to!(Fields!Arg[i]);
            }
        } else {
            args[0] = readln.chomp.to!Arg;
        }
    } else {
        auto input = readln.split;
        assert(input.length == Args.length);

        static foreach (i; 0..Args.length) {
            args[i] = input[i].to!(Args[i]);
        }
    }
}

void get_lines(Args...)(size_t N, ref Args args)
{
    import std.traits, std.range;

    static foreach (i; 0..Args.length) {
        static assert(isArray!(Args[i]));
        args[i].length = N;
    }

    foreach (i; 0..N) {
        static if (Args.length == 1) {
            get(args[0][i]);
        } else {
            auto input = readln.split;
            static foreach (j; 0..Args.length) {
                args[j][i] = input[j].to!(ElementType!(Args[j]));
            }
        }
    }
}

void main()
{
    int T; get(T);
    while (T--) {
        int N; get(N);
        char[] b; get(b);
        char[] a;
        char last;
        foreach (i, c; b) {
            switch (c) {
                case '0':
                    if (last == '1') {
                        a ~= '0';
                        last = '0';
                    } else {
                        a ~= '1';
                        last = '1';
                    }
                    break;
                case '1':
                    if (last == '2') {
                        a ~= '0';
                        last = '1';
                    } else {
                        a ~= '1';
                        last = '2';
                    }
                    break;
                default:
            }
        }
        writeln(a);
    }
}

// Cheese-Cracker: cheese-cracker.github.io

void theCode(){
    int n;
    n = scan!int;
    ll[] res, arr;
    auto w = scan!(dchar[]);
    w.each!(a => arr ~= to!long(a - '0'));
    ll cs = 0, ps = -1;
    for(int i = 0; i < n; ++i){
        res ~= 2 - arr[i];
        if(res[i] == 2) --res[i];
        cs = res[i]+arr[i];
        if(cs == ps){
            res[i] = !res[i];
        }
        cs = res[i]+arr[i];
        write(res[i]);
        ps = cs;
    }
    writeln;
}

void main(){
    long tests = 1;
    tests = scan;        // Toggle!
    while(tests--) theCode();
}

/*********  That's All Folks!  *********/
import std.stdio, std.random, std.functional, std.container, std.algorithm;
import std.numeric, std.range, std.typecons, std.string, std.math, std.conv;
string[] tk; T scan(T=long)(){while(!tk.length)tk = readln.split; string a=tk.front; tk.popFront; return a.to!T;}
T[] scanArray(T=long)(){ auto r = readln.split.to!(T[]); return r; }
void show(A...)(A a){ debug{ foreach(t; a){stderr.write(t, "| ");} stderr.writeln; } }
alias ll = long, tup = Tuple!(long, "x",  long, "y");

import std.algorithm;
import std.conv;
import std.range;
import std.stdio;
import std.string;

void main ()
{
	auto tests = readln.strip.to !(int);
	foreach (test; 0..tests)
	{
		auto n = readln.strip.to !(int);
		auto s = readln.strip.map !(q{a - '0'}).array;
		int [] t;
		int prev = -1;
		foreach (ref c; s)
		{
			auto cur = (c + 1 != prev);
			t ~= cur;
			prev = c + cur;
		}
		writefln !("%(%s%)") (t);
	}
}

import std.stdio, std.conv, std.functional, std.string;
import std.algorithm, std.array, std.container, std.range, std.typecons;
import std.bigint, std.numeric, std.math, std.random;
import core.bitop;

string FMT_F = "%.10f";

static File _f;
void file_io(string fn) { _f = File(fn, "r"); }
static string[] s_rd;
T _RD(T = long)() { while(!s_rd.length) s_rd = readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
T _RD(T = long)(File f) { while(!s_rd.length) s_rd = f.readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
T[] _RDA(T = long)(T fix = 0) { auto r = readln.chomp.split.to!(T[]); r[] += fix; return r; }
T[] _RDA(T = long)(File f, T fix = 0) { auto r = f.readln.chomp.split.to!(T[]); r[] += fix; return r; }
T RD(T = long)() { if (_f.isOpen) return _RD!T(_f); else return _RD!T; }
T[] RDA(T = long)(T fix = 0) { if (_f.isOpen)  return _RDA!T(_f, fix); else return _RDA!T(fix); }

size_t[] MAKE_IDX(alias less = "a < b", Range)(Range range) { auto idx = new size_t[](range.length); makeIndex!(less)(range, idx); return idx;}
size_t MIN_POS(alias less = "a < b", Range)(Range range) { auto r = minPos!(less)(range); return range.length - r.length; }

void chmin(T)(ref T x, T y) { x = min(x, y); } void chmax(T)(ref T x, T y) { x = max(x, y); }
bool inside(T)(T x, T b, T e) { return x >= b && x < e; }
T lcm(T)(T x, T y) { return x * (y / gcd(x, y)); }

//long mod = 10^^9 + 7;
long mod = 998_244_353;
//long mod = 1_000_003;
void moda(ref long x, long y) { x = (x + y) % mod; }
void mods(ref long x, long y) { x = ((x + mod) - (y % mod)) % mod; }
void modm(ref long x, long y) { x = (x * y) % mod; }
void modpow(ref long x, long y) { if (!y) { x = 1; return; } auto t = x; x.modpow(y>>1); x.modm(x); if (y&1) x.modm(t); }
void modd(ref long x, long y) { y.modpow(mod - 2); x.modm(y); }

void main()
{
	auto t = RD!int;
	auto ans = new string[](t);
	foreach (ti; 0..t)
	{
		auto n = RD!int;
		auto b = RD!string;

		ans[ti] ~= '1';
		long x;
		if (b[0] == '1')
			x = 2;
		else
			x = 1;

		foreach (i; 1..n)
		{
			if (x == 2)
			{
				x = 1;
				if (b[i] == '0')
					ans[ti] ~= '1';
				else
					ans[ti] ~= '0';
			}
			else if (x == 1)
			{
				if (b[i] == '0')
				{
					ans[ti] ~= '0';
					x = 0;
				}
				else
				{
					ans[ti] ~= '1';
					x = 2;
				}
			}
			else
			{
				ans[ti] ~= '1';
				if (b[i] == '0')
					x = 1;
				else
					x = 2;
			}
		}
	}

	foreach (e; ans)
		writeln(e);
	stdout.flush;
	debug readln;
}


You are given three integers $$$n$$$, $$$d$$$ and $$$k$$$.Your task is to construct an undirected tree on $$$n$$$ vertices with diameter $$$d$$$ and degree of each vertex at most $$$k$$$, or say that it is impossible.An undirected tree is a connected undirected graph with $$$n - 1$$$ edges.Diameter of a tree is the maximum length of a simple path (a path in which each vertex appears at most once) between all pairs of vertices of this tree.Degree of a vertex is the number of edges incident to this vertex (i.e. for a vertex $$$u$$$ it is the number of edges $$$(u, v)$$$ that belong to the tree, where $$$v$$$ is any other vertex of a tree).

The first line of the input contains three integers $$$n$$$, $$$d$$$ and $$$k$$$ ($$$1 \le n, d, k \le 4 \cdot 10^5$$$).

If there is no tree satisfying the conditions above, print only one word "NO" (without quotes). Otherwise in the first line print "YES" (without quotes), and then print $$$n - 1$$$ lines describing edges of a tree satisfying the conditions above. Vertices of the tree must be numbered from $$$1$$$ to $$$n$$$. You can print edges and vertices connected by an edge in any order. If there are multiple answers, print any of them.1

import std.algorithm;
import std.array;
import std.bitmanip;
import std.container;
import std.conv;
import std.functional;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.typecons;
import std.range.interfaces;

void main()
{
    int n, d, k;
    readf("%s %s %s", &n, &d, &k);
    readln;

    if (k == 1) {
        if (n == 2 && d == 1) {
            writeln("YES");
            writeln("1 2");
            return;
        }

        writeln("NO");
        return;
    }

    if (d > n-1) {
        writeln("NO");
        return;
    }

    Tuple!(int, int)[] ans;
    auto nxt = 1;

    void go(int v, int h) {
        debug { writeln(v, ' ', h); }

        auto dg = v == 1 ? 0 : 1;
        foreach (i; dg .. k) {
            if (nxt == n) break;

            auto hleft = i == dg ? h+1 : max(h + 1, d - h + 1);
            if (hleft <= d) {
                ++nxt;
                ans ~= tuple(v, nxt);
                if (hleft < d) {
                    go(nxt, hleft);
                }
            }
        }
    }

    go(1, 0);

    if (nxt < n) {
        writeln("NO");
        return;
    }

    writeln("YES");
    ans.each!(t => writeln(t[0], ' ', t[1]));
}

import std.algorithm;
import std.array;
import std.bitmanip;
import std.container;
import std.conv;
import std.functional;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.typecons;
import std.range.interfaces;

void main()
{
    int n, d, k;
    readf("%s %s %s", &n, &d, &k);
    readln;

    if (k == 1) {
        if (n == 2 && d == 1) {
            writeln("YES");
            writeln("1 2");
            return;
        }

        writeln("NO");
        return;
    }

    if (d > n) {
        writeln("NO");
        return;
    }

    Tuple!(int, int)[] ans;
    auto nxt = 1;

    void go(int v, int h) {
        if (h == d) return;

        auto deg = v == 1 ? 0 : 1;
        foreach (_; deg .. k) {
            if (nxt == n) break;

            ++nxt;
            ans ~= tuple(v, nxt);
            go(nxt, h + 1);
        }
    }

    go(1, 1);

    if (nxt < n) {
        writeln("NO");
        return;
    }

    writeln("YES");
    ans.each!(t => writeln(t[0], ' ', t[1]));
}

import std.algorithm;
import std.array;
import std.bitmanip;
import std.container;
import std.conv;
import std.functional;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.typecons;
import std.range.interfaces;

void main()
{
    int n, d, k;
    readf("%s %s %s", &n, &d, &k);
    readln;

    if (k == 1) {
        if (n == 2 && d == 1) {
            writeln("YES");
            writeln("1 2");
            return;
        }

        writeln("NO");
        return;
    }

    if (d > n) {
        writeln("NO");
        return;
    }

    Tuple!(int, int)[] ans;
    auto nxt = 1;

    void go(int v, int h) {
        debug { writeln(v, ' ', h); }

        auto dg = v == 1 ? 0 : 1;
        foreach (i; dg .. k) {
            if (nxt == n) break;

            auto hleft = i == dg ? h+1 : max(h + 1, d - h + 1);
            if (hleft <= d) {
                ++nxt;
                ans ~= tuple(v, nxt);
                if (hleft < d) {
                    go(nxt, hleft);
                }
            }
        }
    }

    go(1, 0);

    if (nxt < n) {
        writeln("NO");
        return;
    }

    writeln("YES");
    ans.each!(t => writeln(t[0], ' ', t[1]));
}

import std.algorithm;
import std.array;
import std.bitmanip;
import std.container;
import std.conv;
import std.functional;
import std.math;
import std.range;
import std.stdio;
import std.string;
import std.typecons;
import std.range.interfaces;

void main()
{
    int n, d, k;
    readf("%s %s %s", &n, &d, &k);
    readln;

    if (k == 1) {
        if (n == 2 && d == 1) {
            writeln("YES");
            writeln("1 2");
            return;
        }

        writeln("NO");
        return;
    }

    if (d > n) {
        writeln("NO");
        return;
    }

    Tuple!(int, int)[] ans;
    auto nxt = 1;

    void go(int v, int h) {
        if (h == d) return;

        foreach (i; 0 .. k) {
            if (nxt == n) break;

            ++nxt;
            ans ~= tuple(v, nxt);
            go(nxt, h + 1);
        }
    }

    go(1, 1);

    if (nxt < n) {
        writeln("NO");
        return;
    }

    writeln("YES");
    ans.each!(t => writeln(t[0], ' ', t[1]));
}


You are given an array $$$a[0 \ldots n-1]$$$ of length $$$n$$$ which consists of non-negative integers. Note that array indices start from zero.An array is called good if the parity of each index matches the parity of the element at that index. More formally, an array is good if for all $$$i$$$ ($$$0 \le i \le n - 1$$$) the equality $$$i \bmod 2 = a[i] \bmod 2$$$ holds, where $$$x \bmod 2$$$ is the remainder of dividing $$$x$$$ by 2.For example, the arrays [$$$0, 5, 2, 1$$$] and [$$$0, 17, 0, 3$$$] are good, and the array [$$$2, 4, 6, 7$$$] is bad, because for $$$i=1$$$, the parities of $$$i$$$ and $$$a[i]$$$ are different: $$$i \bmod 2 = 1 \bmod 2 = 1$$$, but $$$a[i] \bmod 2 = 4 \bmod 2 = 0$$$.In one move, you can take any two elements of the array and swap them (these elements are not necessarily adjacent).Find the minimum number of moves in which you can make the array $$$a$$$ good, or say that this is not possible.

The first line contains a single integer $$$t$$$ ($$$1 \le t \le 1000$$$) — the number of test cases in the test. Then $$$t$$$ test cases follow. Each test case starts with a line containing an integer $$$n$$$ ($$$1 \le n \le 40$$$) — the length of the array $$$a$$$. The next line contains $$$n$$$ integers $$$a_0, a_1, \ldots, a_{n-1}$$$ ($$$0 \le a_i \le 1000$$$) — the initial array.

For each test case, output a single integer — the minimum number of moves to make the given array $$$a$$$ good, or -1 if this is not possible.

NoteIn the first test case, in the first move, you can swap the elements with indices $$$0$$$ and $$$1$$$, and in the second move, you can swap the elements with indices $$$2$$$ and $$$3$$$.In the second test case, in the first move, you need to swap the elements with indices $$$0$$$ and $$$1$$$.In the third test case, you cannot make the array good.

import std.stdio;
import std.string : split, strip;
import std.algorithm : map, fold;
import std.conv : to;
import std.range : enumerate;
import std.typecons : tuple;

void main()
{
  int t;
  readf!"%d\n"(t);

  foreach (i; 0..t) {
    int n;
    readf!"%d\n"(n);
    auto a = readln.strip.split.map!(to!int);
    auto d = a.enumerate.fold!((a, b) {
      if (b.index % 2 != b.value % 2) {
        a[b.index % 2]++;
      }
      return a;
    })([0, 0]);

    if (d[0] == d[1]) {
      writeln(d[0]);
    } else {
      writeln(-1);
    }
  }
}

import std.stdio, std.conv, std.functional, std.string;
import std.algorithm, std.array, std.container, std.range, std.typecons;
import std.bigint, std.numeric, std.math, std.random;
import core.bitop;

string FMT_F = "%.10f";

static File _f;
void file_io(string fn) { _f = File(fn, "r"); }
static string[] s_rd;
T _RD(T = long)() { while(!s_rd.length) s_rd = readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
T _RD(T = long)(File f) { while(!s_rd.length) s_rd = f.readln.chomp.split; string res = s_rd[0]; s_rd.popFront; return res.to!T; }
T[] _RDA(T = long)(T fix = 0) { auto r = readln.chomp.split.to!(T[]); r[] += fix; return r; }
T[] _RDA(T = long)(File f, T fix = 0) { auto r = f.readln.chomp.split.to!(T[]); r[] += fix; return r; }
T RD(T = long)() { if (_f.isOpen) return _RD!T(_f); else return _RD!T; }
T[] RDA(T = long)(T fix = 0) { if (_f.isOpen)  return _RDA!T(_f, fix); else return _RDA!T(fix); }

size_t[] MAKE_IDX(alias less = "a < b", Range)(Range range) { auto idx = new size_t[](range.length); makeIndex!(less)(range, idx); return idx;}
size_t MIN_POS(alias less = "a < b", Range)(Range range) { auto r = minPos!(less)(range); return range.length - r.length; }

void chmin(T)(ref T x, T y) { x = min(x, y); } void chmax(T)(ref T x, T y) { x = max(x, y); }
bool inside(T)(T x, T b, T e) { return x >= b && x < e; }
T lcm(T)(T x, T y) { return x * (y / gcd(x, y)); }

//long mod = 10^^9 + 7;
long mod = 998_244_353;
//long mod = 1_000_003;
void moda(T)(ref T x, T y) { x = (x + y) % mod; }
void mods(T)(ref T x, T y) { x = ((x + mod) - (y % mod)) % mod; }
void modm(T)(ref T x, T y) { x = (x * y) % mod; }
void modpow(T)(ref T x, T y) { if (!y) { x = 1; return; } auto t = x; x.modpow(y>>1); x.modm(x); if (y&1) x.modm(t); }
void modd(T)(ref T x, T y) { y.modpow(mod - 2); x.modm(y); }

void main()
{
	auto t = RD!int;
	auto ans = new int[](t);
	foreach (ti; 0..t)
	{
		auto n = RD!int;
		auto a = RDA!int;
		int cnt0, cnt1;
		foreach (i; 0..n)
		{
			if (i % 2 != a[i] % 2)
			{
				if (i % 2)
					++cnt1;
				else
					++cnt0;
			}
		}
		if (cnt0 != cnt1)
		{
			ans[ti] = -1;
		}
		else
		{
			ans[ti] = cnt0;
		}
	}

	foreach (e; ans)
	{
		writeln(e);
	}
	stdout.flush;
	debug readln;
}