排队[动态规划]

一.背景

二.分析

设a[i]表示长度为i的排队方法数,b[i]表示长度为i且结尾是M的排队方法数,c[i]表示长度为i且结尾是FF的排队方法数。显然,有关系a[i]=b[i]+c[i]

现在我们开始考虑各个部分。

对于b[i]:b[i]一定以M结尾,那么前 n-1 位无论是F还是M都合法。则有b[i]=a[i-1]

对于c[i]:c[i]一定以FF结尾

第一种情况:前i-1位以FF结尾,最后一位是F

第二种情况:前i-2位以M结尾,最后两位是FF

因此,c[i]=c[i-1]+b[i-2]

所以我们得到了:

a[i]=b[i]+c[i]

b[i]=a[i-1]

c[i]=c[i-1]+b[i-2]

数学推导:

根据第一个式子和第二个式子可以得到c[i]=a[i]-b[i]=a[i]-a[i-1]

带入第三个式子:a[i]-a[i-1]=a[i-1]-a[i-2]+a[i-3]

整理得:a[i]=2*a[i-1]-a[i-2]+a[i-3]

三.代码

#include<bits/stdc++.h>
using namespace std;
const int M=1e5+10;

long long n,dp[M]; 

int main(){
	ios::sync_with_stdio(false);
    cin.tie(0);cout.tie(0);
    dp[0]=1;dp[1]=1;dp[2]=2;
    for(int i=3;i<=50;i++){
    	dp[i]=2*dp[i-1]-dp[i-2]+dp[i-3];
	}
    while(cin>>n){
    	cout<<dp[n]<<endl;
	}
	return 0;
}
posted @ 2026-07-06 17:11  zGinkh  阅读(4)  评论(0)    收藏  举报