Problem:
Score : 1100 points

Problem Statement

You are given integers N, K, and an integer sequence A of length M.

An integer sequence where each element is between 1 and K (inclusive) is said to be colorful when there exists a contiguous subsequence of length K of the sequence that contains one occurrence of each integer between 1 and K (inclusive).

For every colorful integer sequence of length N, count the number of the contiguous subsequences of that sequence which coincide with A, then find the sum of all the counts.
Here, the answer can be extremely large, so find the sum modulo 10^9+7.

Constraints

1 \leq N \leq 25000

1 \leq K \leq 400

1 \leq M \leq N

1 \leq A_i \leq K

All values in input are integers.

Input

Input is given from Standard Input in the following format:

N K M
A_1 A_2 ... A_M

Output

For every colorful integer sequence of length N, count the number of the contiguous subsequences of that sequence which coincide with A, then print the sum of all the counts modulo 10^9+7.

Sample Input 1

3 2 1
1

Sample Output 1

9

There are six colorful sequences of length 3: (1,1,2), (1,2,1), (1,2,2), (2,1,1), (2,1,2) and (2,2,1).
The numbers of the contiguous subsequences of these sequences that coincide with A=(1) are 2, 2, 1, 2, 1 and 1, respectively.
Thus, the answer is their sum, 9.

Sample Input 2

4 2 2
1 2

Sample Output 2

12

Sample Input 3

7 4 5
1 2 3 1 2

Sample Output 3

17

Sample Input 4

5 4 3
1 1 1

Sample Output 4

0

Sample Input 5

10 3 5
1 1 2 3 3

Sample Output 5

1458

Sample Input 6

25000 400 4
3 7 31 127

Sample Output 6

923966268

Sample Input 7

9954 310 12
267 193 278 294 6 63 86 166 157 193 168 43

Sample Output 7

979180369

Solution in C# (Mono 4.6.2.0) (judge verdict: Time Limit Exceeded)

using System;
using System.Collections.Generic;
using System.Linq;
using System.Diagnostics;
using Debug = System.Diagnostics.Trace;
using SB = System.Text.StringBuilder;
using Number = System.Int64;
using System.Numerics;
using static System.Math;
namespace Program {
    public class Solver {
        Random rnd = new Random();
        public void Solve() {
            var n = ri;
            var k = ri;
            if (k == 1)
            {
                Console.WriteLine(1);
                return;
            }
            var m = ri;
            var a = Enumerate(m, x => ri - 1);
            ModInt ans = 0;
            if (isColorful(k, a))
            {
                ans = n - m + 1;
                ans *= ModInt.Pow(k, n - m);
                Console.WriteLine(ans);
                return;
            }
            var S = new HashSet<int>();
            var T = new HashSet<int>();
            foreach (var x in a)
                if (!S.Add(x)) break;
            foreach (var x in a.Reverse())
                if (!T.Add(x)) break;
            Debug.WriteLine(S.Count);
            Debug.WriteLine(T.Count);
            if (S.Count != m)
            {
                var L = calcDP(S.Count, k);
                var R = calcDP(T.Count, k);
                for (int len = 0; len <= n - m; len++)
                {
                    ans += L[0][len] * R[1][n - m - len];
                    ans += L[1][len] * R[0][n - m - len];
                    ans += L[1][len] * R[1][n - m - len];
                }

                Console.WriteLine(ans);
            }
            else
            {
                Console.WriteLine(calc(n, k, m));
            }

        }
        ModInt calc(int N, int K, int m) {
            var dp = new ModInt[K + 1, 2, 2];

            dp[0, 0, 0] = 1;

            for (int i = 0; i < N; i++)
            {
                var next = new ModInt[K + 1, 2, 2];
                var push = new ModInt[K + 1, 2, 2];
                for (int j = 0; j <= K; j++)
                    for (int k = 0; k < 2; k++)
                        for (int p = 0; p < 2; p++)
                        {
                            if (j < K)
                            {
                                var nk = j == K - 1 ? 1 : k;
                                next[j + 1, nk, p] += (K - j) * dp[j, k, p];
                            }
                            push[j, k, p] += dp[j, k, p];
                        }
                for (int j = K; j > 0; j--)
                    for (int k = 0; k < 2; k++)
                        for (int p = 0; p < 2; p++)
                        {
                            next[j, k, p] += push[j, k, p];
                            push[j - 1, k, p] += push[j, k, p];
                        }
                for (int j = m; j <= K; j++)
                    for (int k = 0; k < 2; k++)
                        next[j, k, 1] += next[j, k, 0];
                dp = next;
            }


            ModInt ans = 0;
            for (int i = 0; i <= K; i++)
                ans += dp[i, 1, 1];
            for (int i = 1; i <= K - m; i++)
                ans *= i;
            for (int j = 1; j <= K; j++) ans *= ModInt.Inverse(j);
            return ans;
        }
        ModInt[][] calcDP(int p, int K) {
            var dp = Enumerate(25050, x => new ModInt[K]);
            var ep = new ModInt[25050];
            var fp = new ModInt[25050];
            dp[0][p] = 1;
            for (int i = 0; i <= 25000; i++)
            {
                ep[i + 1] += K * ep[i];
                var push = new ModInt[K];
                for (int j = 1; j < K; j++)
                {
                    fp[i] += dp[i][j];
                    if (j == K - 1) ep[i + 1] += dp[i][j];
                    else dp[i + 1][j + 1] += dp[i][j] * (K - j);
                    push[j] += dp[i][j];
                }
                for (int j = K - 1; j > 0; j--)
                {
                    dp[i + 1][j] += push[j];
                    push[j - 1] += push[j];
                }
            }
            return new ModInt[][] { fp, ep };
        }
        bool isColorful(int k, int[] a) {
            if (a.Length < k) return false;
            var cnt = new int[k];
            for (int i = 0; i < k; i++)
                cnt[a[i]]++;
            var ok = cnt.Count(x => x == 1);
            if (ok == k) return true;
            for (int i = k; i < a.Length; i++)
            {
                if (cnt[a[i - k]] == 1) ok--;
                cnt[a[i - k]]--;
                if (cnt[a[i - k]] == 1) ok++;

                if (cnt[a[i]] == 1) ok--;
                cnt[a[i]]++;
                if (cnt[a[i]] == 1) ok++;
                if (ok == k) return true;
            }
            return false;

        }
        const long INF = 1L << 60;
        //static int[] dx = { -1, 0, 1, 0 };
        //static int[] dy = { 0, 1, 0, -1 };

        int ri { get { return sc.Integer(); } }
        long rl { get { return sc.Long(); } }
        double rd { get { return sc.Double(); } }
        string rs { get { return sc.Scan(); } }
        public IO.StreamScanner sc = new IO.StreamScanner(Console.OpenStandardInput());

        static T[] Enumerate<T>(int n, Func<int, T> f) {
            var a = new T[n];
            for (int i = 0; i < n; ++i) a[i] = f(i);
            return a;
        }
        static public void Swap<T>(ref T a, ref T b) { var tmp = a; a = b; b = tmp; }
    }
}
#region main
static class Ex {
    static public string AsString(this IEnumerable<char> ie) { return new string(ie.ToArray()); }
    static public string AsJoinedString<T>(this IEnumerable<T> ie, string st = " ") {
        return string.Join(st, ie);
    }
    static public void Main() {
        Console.SetOut(new Program.IO.Printer(Console.OpenStandardOutput()) { AutoFlush = true });
        var solver = new Program.Solver();
        try
        {
            solver.Solve();
            Console.Out.Flush();
        }
        catch { }
    }
}
#endregion
#region Ex
namespace Program.IO {
    using System.Globalization;
    using System.IO;
    using System.Text;

    public class Printer: StreamWriter {
        public override IFormatProvider FormatProvider { get { return CultureInfo.InvariantCulture; } }
        public Printer(Stream stream) : base(stream, new UTF8Encoding(false, true)) { }
    }

    public class StreamScanner {
        public StreamScanner(Stream stream) { str = stream; }

        public readonly Stream str;
        private readonly byte[] buf = new byte[1024];
        private int len, ptr;
        public bool isEof = false;
        public bool IsEndOfStream { get { return isEof; } }

        private byte read() {
            if (isEof) return 0;
            if (ptr >= len)
            {
                ptr = 0;
                if ((len = str.Read(buf, 0, 1024)) <= 0)
                {
                    isEof = true;
                    return 0;
                }
            }
            return buf[ptr++];
        }

        public char Char() {
            byte b = 0;
            do b = read(); while ((b < 33 || 126 < b) && !isEof);
            return (char)b;
        }
        public string Scan() {
            var sb = new StringBuilder();
            for (var b = Char(); b >= 33 && b <= 126; b = (char)read()) sb.Append(b);
            return sb.ToString();
        }
        public string ScanLine() {
            var sb = new StringBuilder();
            for (var b = Char(); b != '\n' && b != 0; b = (char)read())
                if (b != '\r') sb.Append(b);
            return sb.ToString();
        }
        public long Long() { return isEof ? long.MinValue : long.Parse(Scan()); }
        public int Integer() { return isEof ? int.MinValue : int.Parse(Scan()); }
        public double Double() { return isEof ? double.NaN : double.Parse(Scan(), CultureInfo.InvariantCulture); }
    }
}
#endregion


public struct ModInt {
    public const long Mod = (int)1e9 + 7;
    public long num;
    public ModInt(long n) { num = n; }
    public override string ToString() { return num.ToString(); }
    public static ModInt operator +(ModInt l, ModInt r) { l.num += r.num; if (l.num >= Mod) l.num -= Mod; return l; }
    public static ModInt operator -(ModInt l, ModInt r) { l.num -= r.num; if (l.num < 0) l.num += Mod; return l; }
    public static ModInt operator *(ModInt l, ModInt r) { return new ModInt(l.num * r.num % Mod); }
    public static implicit operator ModInt(long n) { n %= Mod; if (n < 0) n += Mod; return new ModInt(n); }

    public static ModInt Pow(ModInt v, long k) { return Pow(v.num, k); }
    public static ModInt Pow(long v, long k) {
        long ret = 1;
        for (k %= Mod - 1; k > 0; k >>= 1, v = v * v % Mod)
            if ((k & 1) == 1) ret = ret * v % Mod;
        return new ModInt(ret);
    }
    public static ModInt Inverse(ModInt v) { return Pow(v, Mod - 2); }
}