hautoj 1265 Hmz 的女装 【dp】

来源:互联网 发布:灰盒测试知乎 编辑:程序博客网 时间:2024/04/28 01:01


点击打开链接


1265: Hmz 的女装

时间限制: 2 秒  内存限制: 128 MB
提交: 157  解决: 48
提交 状态 

题目描述

Hmz为了女装,想给自己做一个长度为n的花环。现在有k种花可以选取,且花环上相邻花的种类不能相同。
Hmz想知道,如果他要求第l朵花和第r朵花颜色相同,做花环的方案数是多少。这个答案可能会很大,你只要输出答案对10^9+7取模的结果即可。

输入

第一行三个整数n,m,k(1≤n≤100000,1≤m≤100000,1≤k≤100000)
接下来m行,每行两个整数l,r,表示要求第l朵花和第r朵花颜色相同。保证lr且 |(rlmod n| ≠1.

输出

输出m行。对于每一个询问输出一个整数,表示做花环的方案数对10^9+7取模的结果。

样例输入

8 3 2
1 4
2 6
1 3
8 3 3
1 4
2 6
1 3

样例输出

0
2
2
60
108
132


首先很容易想到  l和r 把一条直线分成三段,但是这条线是个环,那么其实就是,把l前面的接在最后面。变成两段。

dp[i][j] 代表 被分开的子段长度为i时 j=0包含l颜色 j=1不含l颜色,j=0之前总方案数。

所以由第i个就能推出来第i+1个。


还有k=2时 的特殊情况。

#include<bits/stdc++.h>#define ll long longusing namespace std;const int mod=1e9+7;const int maxn=1e5+10;int n,m,k,l,r;ll dp[maxn][3];int init(){    dp[0][0]=1;    dp[1][1]=k-1;    for(int i=2;i<=n;++i){        dp[i][0]=(dp[i-1][1]+dp[i-1][2])%mod;        dp[i][1]=dp[i-1][0]*(k-1)%mod;        dp[i][2]=dp[i][0]*(k-2)%mod;    }}int main(){    while(~scanf("%d %d %d",&n,&m,&k)){        init();        while(m--){            scanf("%d %d",&l,&r);            if(l>r) swap(l,r);            if(k==2){                if((r-l-1)%2!=0) printf("2\n");                else printf("0\n");            }            else {                int t1=n-r+l-1;                int t2=r-l-1;                ll ans=(k%mod*dp[t1+1][0]%mod*dp[t2+1][0]%mod)%mod;                printf("%lld\n",ans);            }        }    }    return 0;}


0 0
原创粉丝点击