アイデアは、特に注意を払うように、多くの詳細と依然として困難ではありませんが、。
コード:
書式#include <cstdioを> 書式#include <キュー> 書式#include <CStringの> 書式#include <アルゴリズム> #define N 2005 #define LL長い長いです #defineモッズ十億七 #define setIO(S)freopenは(S ".IN"、 "R"、標準入力) 名前空間stdを使用。 キュー<整数> Q; 文字列str [N]、S [N]。 整数N、M、TOT、CH [N] [10] F [N]、DP [N] [N] [2]、タグ[N]。 空のインサート() { INT I、J、LEN = STRLEN(STR + 1)、P = 0。 以下のための式(I = 1; I <= LEN; ++ I) { もし - CH [P] [STR [I] - '0'] = ++ TOT(CH [P] [STR [i]が '0']!)。 P = CH [P] [STR [I] - '0']。 } タグ[P] = 1。 } 空のビルド() { 私は、jはint型。 (CH [0] [i])とq.push(CH [0] [i])とIF(++ I; I <10、I = 0)ため、 しばらく(!q.empty()) { INT U = q.front(); q.pop()。 タグ[U] | =タグ[F [U]。 以下のための式(I = 0、I <10; ++ I) { INT QR = CH [U] [I]。 もし{CH [U] [I] = CH [F [U] [I](QR!)。継続する; } F [QR] = CH [F [U] [i]は、 q.push(QR)。 } } } メインint型() { // setIO( "入力"); 私は、jはint型。 scanf関数( "%sの%D"、S + 1、&M)。 N = STRLEN(S + 1)。 ため(I 1 =、iが<= M; ++ I)のscanf( "%s" は、STR + 1)、挿入()。 ビルド(); ための式(I = 1; iが<S [1] - '0'; ++ i)が(!タグ[CH [0] [I])DP [1] [CH [0] [I] [0の場合] + = 1; IF(!タグ[CH [0] [S [1] - '0']])DP [1] [CH [0] [S [1] - '0']] [1] = 1。 以下のための式(I = 1、I <N; ++ I) { 用(J = 1、J <10; ++ j)は(!タグ[CH [0] [J])であれば、DP [I + 1] [CH [0] [j] [0] + = 1; 用(J = 0であり、j <= TOT; ++ j)は { (タグ[J])続行。 もし(DP [I] [J] [0]) { 用(int型のk = 0; K <10; ++ K) { IF(タグ[CH [J] [K])続けます。 (DP [I + 1] [CH [J] [K] [0] + = DP [I] [J] [0])%= MOD。 } } IF(DP [I] [J] [1]) { 用(int型のk = 0; K <S [I + 1] - '0'; ++ K) { IF(タグ[CH [J] [K])続けます。 (DP [I + 1] [CH [J] [K] [0] + = DP [I] [J] [1])。 } } IF(タグ[CH [J] [S [I + 1] - '0']])続けます。 DP [I + 1]、[CH [J] [S [I + 1] - '0']] [1] | = DP [I] [J] [1]; } } INT年= 0; 以下のための式(I = 0; I <= TOT; ++ I) { (タグ[I])を続ける場合。 (ANS + = DP [n]は[I] [0])%= MOD。 (ANS + = DP [n]は[I] [1])%= MOD。 } printf( "%dの\ n" は、ANS)。 0を返します。 }