jzoj3466. 【NOIP2013模拟联考6】选课(select)

版权声明:233 https://blog.csdn.net/gmh77/article/details/81125429

题目描述

Description
你真的认为选课是那么容易的事吗?HYSBZ的ZY同志告诉你,原来选课也会让人产生一种想要回到火星的感觉。假设你的一周有n天,那么ZY编写的选课系统就会给你n堂课。但是该系统不允许在星期i和星期i+1的时候选第i堂课,也不允许你在星期n和星期一的时候选第n堂课。然后连你自己也搞不清哪种选课方案合法,哪种选课不合法了。你只想知道,你到底有多少种合法的选课方案。

Input
有多组数据,请读到文件末结束。

对于每组数据仅一行,1个正整数 n。
Output
对于每组输出只有一行,1个非负整数,为选课方案数量 mod (10^9+7).

Sample Input
2

4
Sample Output
0

2

【样例解释】

对于样例二:

周一上第二堂课,周二上第三堂课,周三上第四堂课,周四上第一堂课;

周一上第三堂课,周二上第四堂课,周三上第一堂课,周四上第二堂课。

共2种选课方案。

Data Constraint
对于第i组数据,n<=10*i, 1<=i<=3

对于100%的数据:1<=n<=100000

心路历程

考试刚开始时,写了个暴力想找规律
于是输入了1~10(按顺序),结果是
0 0 1 3 16 96 675 5413 48800 488592

于是瞎找规律
(1+3)*4+0=16
(3+16)*5+1=96
(16+96)*6+3=675

欸?
F [ n ] = ( F [ n 1 ] + F [ n 2 ] ) ( n 1 ) + F [ n 3 ]
ヾ(≧▽≦*)o


然后,我发现
我™暴力没清答案!
_(:з)∠)_


再一想,发现我求得其实是答案的前缀和
于是这里写图片描述
这里写图片描述

code

没什么好说的。。。

#include <iostream>
#include <cstdlib>
#include <cstdio>
#define fo(a,b,c) for (a=b; a<=c; a++)
#define fd(a,b,c) for (a=b; a>=c; a--)
#define mod 1000000007
using namespace std;

long long f[100001];
int n,ans,i;

int main()
{
    f[0]=0;
    f[1]=0;
    f[2]=0;
    f[3]=1;
    f[4]=3;
    fo(i,5,100000)
    f[i]=((long long)(f[i-1]+f[i-2])*(i-1)%mod+f[i-3])%mod;

    while (scanf("%d",&n)!=EOF)
    printf("%lld\n",(f[n]-f[n-1]+mod)%mod);
}

猜你喜欢

转载自blog.csdn.net/gmh77/article/details/81125429