Social networking web sites are very popular these days. I am not mentioning any names because you know better than me. People do have a lot of e-friends now, "you may not know his real identity but he is your friend". Sometimes, there can be rivalries between people, and thus people gets blocked or deleted. And these rivalries don't have to be necessarily commutative. That means x may think y as his enemy, but y may or may not think so.
However, what if you get the opportunity to see all your e-friends live? Since you like social networks very much, you planned to arrange a get-together with your e-friends. So, you invited n of your e-friends in your home. For simplicity, you numbered them from 1 to n. They were your friends, but rivalries existed amongst many of them. You asked them to form a queue such that they can get food from the table. And you will serve foods one by one. But your friends demanded that, no enemy should be the next person in the queue. That means if x thinks that y is his enemy and x's position in the queue is i, then y's position shouldn't be i-1.
So, it became very complex. That's why you decided to add a dissatisfaction index k if one's demand is not fulfilled. And the total dissatisfaction index is the summation of all the dissatisfaction indexes. Now you know the rivalries and the maximum total dissatisfaction index you may allow, you want to find the total number of possible arrangements.
Input
Input starts with an integer T (≤ 30), denoting the number of test cases.
Each case starts with three integers n (1 ≤ n ≤ 12), k (0 ≤ k ≤ 106) and q (1 ≤ q ≤ 1000) which denotes the number of queries. Then there will be n lines. The ith line contains an integer ti (0 ≤ ti < n)and ids of ti distinct friends. It means ith person thinks the ti listed persons as his enemy. Each of the next q lines contains an integer r (0 ≤ r ≤ 108) denoting the total allowable dissatisfaction index.
Output
For each case, print the case number first. Then for each query, print the total number of arrangements possible not exceeding the given total dissatisfaction index.
Sample Input | Output for Sample Input |
1 2 10 2 1 2 0 10 5 | Case 1: 2 1 |
输入n,K,q,代表有n个人,下面有n行,第i行的第一个数表示第i个人有x个敌人,如果一个人站在他敌人的后面,就会产生K不满意度。q表示有q个询问,每次询问比X不满意度小的站法有多少种。
dp[i][j][k],i表示队伍状态,j表示最后一个站的是j,k表示有k个不满意的。
#include<cstdio>
#include<cstring>
#include<iostream>
#include<algorithm>
#define LL long long
using namespace std;
int dp[1<<13][15][15];
int main(void)
{
int T,n,K,q,i,j,k,l;
int a[15][15];
scanf("%d",&T);
int cas = 1;
while(T--)
{
memset(a,0,sizeof(a));
memset(dp,0,sizeof(dp));
scanf("%d%d%d",&n,&K,&q);
for(i=0;i<n;i++)
{
int x,y;
scanf("%d",&x);
while(x--)
{
scanf("%d",&y);
a[i][y-1] = 1;
}
}
for(i=0;i<n;i++)
dp[1<<i][i][0] = 1;
for(i=0;i<(1<<n);i++)
{
int cnt = 0;
for(j=0;j<n;j++)
if((1<<j)&i)
cnt++;
for(j=0;j<n;j++)
{
if((1<<j)&i == 0)
continue;
for(k=0;k<cnt;k++)
{
for(l=0;l<n;l++)
{
if((1<<l)&i)
continue;
dp[i|(1<<l)][l][k+a[l][j]] += dp[i][j][k];
}
}
}
}
printf("Case %d:\n",cas++);
while(q--)
{
int x;
scanf("%d",&x);
LL sum = 0;
for(i=0;i<n;i++)
{
for(j=0;j<n;j++)
{
if(j*K>x)
break;
sum += dp[(1<<n)-1][i][j];
}
}
printf("%lld\n",sum);
}
}
return 0;
}