母函数
来源:互联网 发布:ubuntu vi复制命令 编辑:程序博客网 时间:2024/04/28 07:47
有1克、2克、3克、4克的砝码各一枚,能称出哪几种重量?每种重量各有几种可能方案?
考虑用母函数来接吻这个问题:
我们假设x表示砝码,x的指数表示砝码的重量,这样:
1个1克的砝码可以用函数1+x表示,
1个2克的砝码可以用函数1+x2表示,
1个3克的砝码可以用函数1+x3表示,
1个4克的砝码可以用函数1+x4表示,
几种砝码的组合可以称重的情况,可以用以上几个函数的乘积表示:
(1+x)(1+x2)(1+x3)(1+x4)
=(1+x+x2+x3)(1+x3+x4+x7)
=1+x+x2+2x3+2x4+2x5+2x6+2x7+x8+x9+x10
从上面的函数知道:可称出从1克到10克,系数便是方案数。(!!!经典!!!)
例如右端有2x5 项,即称出5克的方案有2:5=3+2=4+1;同样,6=1+2+3=4+2;10=1+2+3+4。
- 整数拆分
输入一个整数n,把它拆成若干个整数相加,输出有多少种拆分的方法。
比如:4=3+1=2+2=2+1+1=1+1+1+1,有5种。
解:
所谓整数拆分即把整数分解成若干整数的和(相当于把n个无区别的球放到n个无标志的盒子,盒子允许空,也允许放多于一个球)。
G(x)=(1+x+x^2+…)(1+x^2+x^4+…)(1+x^3+x^6+…)…
#include <stdio.h>
#include <string.h>
int main()
{
int c1[200],c2[200]; //c1保存当前表达式里各项的系数,c2是中间量
int n,i,j,k;
while(scanf("%d",&n)!=EOF)
{
for(i=0;i<=n;i++) //n拆分的数必定小于或等于n,所以只用从0遍历到n,即母函数的第1个括号里的表达式只能是1+x+x^2+…+x^n
{
c1[i]=1; //初始化c1[],c1[]的下标是项的指数,值是项的系数
c2[i]=0;
}
for(i=2;i<=n;i++) //后面有n-1个表达式(括号里的式子),要展开n-1次,i指第i个表达式
{
for(j=0;j<=n;j++)
{
for (k=0;k+j<=n;k=k+i)
{
c2[k+j]+=c1[j]; //只用保留指数<=n的项,所以k+j<=n
} //j指当前表达式里项的第j个项,k指后一个表达式里项的指数,k=k+i
} //两个相邻表达式展开
for(j=0;j<=n;j++)
{
c1[j]=c2[j];
c2[j]=0;
} //每展开一次,就将c1[]更新,c2[]归0
}
printf("%d\n",c1[n]);
}
return 0;
}
- 钱币组合:
有面值为1,2,5的3种硬币,输入各硬币的个数,求最小的一个不能组合的成的价值。
比如输入1 1 3,输出4
解:
G(x)=(1+x+x^2+…)(1+x^2+x^4+…)(1+x^5+x^10+…)
3种面值,所以只有3个括号表达式。
#include <stdio.h>#include <string.h>int main(){ int a,b,c,i,j,k,sum; int c1[8008],c2[8008]; int elem[3]={1,2,5}; int num[4]; while(scanf("%d%d%d",&a,&b,&c)!=EOF) { if(a==0&&b==0&&c==0) break; sum=1*a+2*b+5*c; num[1]=a; num[2]=b; num[3]=c; //num[]存放括号内表达式的项的个数 memset(c1,0,sizeof(c1)); memset(c2,0,sizeof(c2)); //c1[],c2[]全部归0 for(i=0;i<=a;i=i+elem[0]) //初始化第1个表达式里各项的系数 c1[i]=1; for(i=2;i<=3;i++) { for(j=0;j<=sum;j++) { for(k=0;k<=num[i]*elem[i-1]&&k+j<=sum;k=k+elem[i-1]) { c2[j+k]+=c1[j]; } } for(j=0;j<=sum+1;j++) { c1[j]=c2[j]; c2[j]=0; } } for(i=0;i<=sum+1;i++) { if(c1[i]==0) { printf("%d\n",i); break; } } } return 0;}
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 母函数
- 开源项目代码阅读小技巧
- NYOJ 22 素数求和问题 2013年8月20日
- poj 3335 Rotating Scoreboard(半平面交)
- _declspec(naked) 使用(裸函数)
- 在c文档中C2143问题出现的一种方式及解决方法
- 母函数
- 扩展的欧几里得
- 大数运算(加减乘除)
- @Override must override a superclass method
- 并查集(HDOJ 1856)
- 种类并查集(POJ 1703)
- 最小生成树(HDOJ 1863)
- HDOJ(1728)逃离迷宫
- GestureDetector类及其用法