Description
A little kid loves to write digits in LC display style, but he would like to put two consecutive digits very close to each other. Sometimes, that makes the number he writes ambiguous.
In LC display style, each digit is written as below:
0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 |
---|---|---|---|---|---|---|---|---|---|
_ | | |_| | | | | _ _| |_ | _ _| _| | |_| | | _ |_ _| | _ |_ |_| | _ | | | _ |_| |_| | _ |_| _| |
As the table shown above, in LC display style, each digit is written in 3 rows and 3 columns. The little kid always overlaps the last column of the previous digit and the first column of the next digit.
Please help his parents to count the number of different ways to translate the weird 'image'.
There are multiple test cases. The first line of input contains an integer T (T ≤ 1500) indicating the number of test cases. Then T test cases follow.
The first line of each case contains one integer: n (n ≤ 104) -- the number of digits that the little kid writes.
Then each of the following 3 lines contains exactly 2n+1 characters -- represents the number written by the kid.
6 1 | | 1 _ |_| |_ 1 | | 1 _ |_| |_| 2 _ |_| |_| 2 _ _ _|_ |_ _|
0 0 1 1 3 1
#include<iostream>
#include<cstdio>
#include<cstring>
#include<math.h>
using namespace std;
const int N=1e5+10;
const int mod=1e9+7;
int T,n;
char s[3][N];
long long dp[N][10];
int get(int x,int y)
{
x=(x-1)*2;
if (s[1][x]==' '&&(y==0||y==4||y==5||y==6||y==8||y==9)) return 0;
if (s[2][x]==' '&&(y==0||y==2||y==6||y==8)) return 0;
x++;
if (s[0][x]==' '&& y!=1&&y!=4) return 0;
if (s[0][x]=='_'&& (y==1||y==4)) return 0;
if (s[1][x]==' '&&y!=1&&y!=0&&y!=7) return 0;
if (s[1][x]=='_'&&(y==1||y==0||y==7)) return 0;
if (s[2][x]==' '&&y!=1&&y!=4&&y!=7) return 0;
if (s[2][x]=='_'&&(y==1||y==4||y==7)) return 0;
x++;
if (s[1][x]==' '&&(y!=5&&y!=6)) return 0;
if (s[2][x]==' '&&y!=2) return 0;
return 1;
}
int check(int x,int y,int g)
{
int a = (x!=5&&x!=6&&x!=-1)||(y!=1&&y!=2&&y!=3&&y!=7&&y!=-1);
int b = (x!=2&&x!=-1)||(y!=1&&y!=3&&y!=4&&y!=5&&y!=7&&y!=9&&y!=-1);
g=(g-1)*2;
if (s[1][g]=='|' && !a) return 0;
if (s[1][g]==' ' && a) return 0;
if (s[2][g]=='|' && !b) return 0;
if (s[2][g]==' ' && b) return 0;
return 1;
}
int main()
{
for (scanf("%d",&T);T--;)
{
scanf("%d",&n); getchar();
gets(s[0]); gets(s[1]); gets(s[2]);
for (int j=0;j<3;j++)
{
int len=strlen(s[j]);
for (int i=0;i<=2*n;i++)
{
if (i>=len) s[j][i]=' ';
}
}
//puts(s[0]+1); puts(s[1]+1); puts(s[2]+1);
for (int i=0;i<=9;i++)
{
dp[1][i]=get(1,i)&&check(-1,i,1);
}
for (int i=2;i<=n;i++)
{
for (int j=0;j<10;j++)
{
dp[i][j]=0;
if (!get(i,j)) continue;
for (int k=0;k<10;k++)
{
(dp[i][j]+=dp[i-1][k]*check(k,j,i))%=mod;
}
}
}
long long ans=0;
for (int i=0;i<10;i++)
{
(ans+=dp[n][i]*check(i,-1,n+1))%=mod;
}
printf("%lld\n",ans);
}
return 0;
}