洛谷P1077 摆花——题解

博客围绕按顺序放n种花,每种最多放ai盆,共放m盆花求方案数的问题展开。分析了求方案个数的常见思路,排除搜索法,联想到背包问题,用动态规划求解,给出状态及转移方程,还提到边界条件,并给出AC代码链接。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目传送

题目大意:有按顺序放的n种花,相同种类的花放一起,每种花最多放ai盆,共放了m盆花,求放花方案数。

求方案个数一般有以下思路:1、搜索;2、递推/动态规划;3、贪心;4、分治。。。

玄学估计发现,仅是可行解就有非常多的数量,显然搜索不行了。联想到“背包问题的方案总数”,猛然发现:这题不就相当于每个物品的重量都为1,最多选ai个,求放满背包的方案总数吗?尝试写出状态:设dp[k][i]为只可能用前k种花、摆了i盆花的方案数,状态转移方程:(当i大于等于ak时)dp[k][i]=dp[k-1][i-0]+dp[k-1][i-1]+..+dp[k-1][i-ak];(当i小于ak时)dp[k][i]=dp[k-1][i-0]+dp[k-1][i-1]+..+dp[k-1][0]。注意边界条件:a[1][i]=1,i=0,1,...,a1,即只用第一种花摆花时是不能由上面的状态转移方程推出来的。

见AC代码:

 

 1 #include<iostream>
 2 #include<cstdio>
 3 
 4 using namespace std;
 5 
 6 int a[101],n,m,dp[101][101],sum;
 7 
 8 const int mod=1000007;
 9 
10 int main()
11 {
12        scanf("%d%d",&n,&m);
13        for(int i=1;i<=n;i++)
14            scanf("%d",&a[i]);
15        for(int i=0;i<=a[1];i++) dp[1][i]=1;//初始化边界条件 
16        sum=a[1];
17        for(int k=2;k<=n;k++)//花的种类 
18        {
19            sum+=a[k];
20            for(int i=0;i<=sum&&i<=m;i++)//共要摆几个 
21            {
22                for(int j=0;j<=a[k]&&j<=i;j++)//第k种用几个 
23                    dp[k][i]+=dp[k-1][i-j];
24             dp[k][i]%=mod;
25         }
26     }
27     cout<<dp[n][m];
28     return 0;
29 }

 

转载于:https://www.cnblogs.com/InductiveSorting-QYF/p/11039891.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值