蓝桥杯——李白打酒

zzj_sxu 2014-10-03 10:14:28
标题:李白打酒

话说大诗人李白,一生好饮。幸好他从不开车。

一天,他提着酒壶,从家里出来,酒壶中有酒2斗。他边走边唱:

无事街上走,提壶去打酒。
逢店加一倍,遇花喝一斗。

这一路上,他一共遇到店5次,遇到花10次,已知最后一次遇到的是花,他正好把酒喝光了。

请你计算李白遇到店和花的次序,可以把遇店记为a,遇花记为b。则:babaabbabbabbbb 就是合理的次序。像这样的答案一共有多少呢?请你计算出所有可能方案的个数(包含题目给出的)。

注意:通过浏览器提交答案。答案是个整数。不要书写任何多余的内容。

从网上看到下面的这段解法,真心凌乱了,是怎么回事啊,求解答

#include<iostream>
using namespace std;
int sum=0;
int f(int a,int b,int c){
if(a>0)
f(a-1,b,c*2);
if(b>0)
f(a,b-1,c-1);
if(a==0&&b==0&&c==1)
sum=sum+1;
return sum;
}
int main()
{
f(5,9,2);
cout<<sum<<endl;
}




...全文
3044 4 打赏 收藏 转发到动态 举报
写回复
用AI写文章
4 条回复
切换为时间正序
请发表友善的回复…
发表回复
baidu_37914506 2017-03-15
  • 打赏
  • 举报
回复
//李白街上走,提壶去买酒,遇店加一倍,遇花喝一斗,遇到店5次,遇到花10次,酒壶原来有两斗,最后一滴不剩,且最后遇到的是花,问遇店和花的顺序和有多少可能性 //本题是菜鸟做法,大神慎入 #include <stdio.h> void main() { int a,b,c,d,e,f,g,h,i,j,k,l,m,n,o,r,s[15],sum,w,t,z=0,v;//定义路上的15次遇到店和花 for(a=1;a<=2;a++) for(b=1;b<=2;b++) for(c=1;c<=2;c++) for(d=1;d<=2;d++) for(e=1;e<=2;e++) for(f=1;f<=2;f++) for(g=1;g<=2;g++) //每次都有两种可能性共有十五次,2代表遇到店,1代表遇到花 for(h=1;h<=2;h++) for(i=1;i<=2;i++) for(j=1;j<=2;j++) for(k=1;k<=2;k++) for(l=1;l<=2;l++) for(m=1;m<=2;m++) for(n=1;n<=2;n++) { s[0]=a; s[1]=b; s[2]=c; s[3]=d; s[4]=e; s[5]=f; s[6]=g; s[7]=h; s[8]=i; //将每一种可能性都先放在s[]里 s[9]=j; s[10]=k; s[11]=l; s[12]=m; s[13]=n; s[14]=1; sum=0; //每次循环初始化 for(v=0;v<15;v++) sum=sum+s[v]; //求和 if(sum==20)//筛选出遇到5次店面和10次花,恒等于20 { r=2;//每次循环酒壶里的酒初始化 for(w=0;w<15;w++) { t=s[w]; {if(t==2) r=2*r; //利用循环判断,如果s[]为2,则表示遇到店,否则,则是为1,遇到花;遇到店加倍,遇到花喝一斗 else r--; } } if(r==0)//如果酒壶里的酒一滴不剩,则把这种情况输出 { z++; for(t=0;t<15;t++) printf("%d ",s[t]); printf("\n"); } } } printf("\nz=%d\n",z);//最后输出总的种数 }
707wk 2014-10-04
  • 打赏
  • 举报
回复
这题目明显用递归容易解决些。。。
实况灬天河 2014-10-03
  • 打赏
  • 举报
回复
引用 1 楼 brookmill 的回复:
这就是个最简单的动态规划吧。假定先遇到店,然后递归计算剩下的可能;再假定先遇到花,然后递归计算剩下的可能。遇到满足要求的组合就加1.
#include<iostream>
using namespace std;
int sum=0;
int f(int a,int b,int c){  // a:店的总数 b:花的总数减1 c:酒的初值
// 任何初始状况,都有两个可能:先遇到店,或者先遇到花
   if(a>0)
     f(a-1,b,c*2); // 逢店加一倍
   if(b>0)
     f(a,b-1,c-1); // 遇花喝一斗
   if(a==0&&b==0&&c==1) //这个是满足要求的终止条件。没有店剩下,还剩一朵花和一斗酒
     sum=sum+1;
    return sum;
}
int main()
{
    f(5,9,2);
    cout<<sum<<endl;
}
赞一个!传参的时候花只传9,说明还有一斗酒是留给最后一朵花的。哎,递归好神奇……
brookmill 2014-10-03
  • 打赏
  • 举报
回复
这就是个最简单的动态规划吧。假定先遇到店,然后递归计算剩下的可能;再假定先遇到花,然后递归计算剩下的可能。遇到满足要求的组合就加1.
#include<iostream>
using namespace std;
int sum=0;
int f(int a,int b,int c){  // a:店的总数 b:花的总数减1 c:酒的初值
// 任何初始状况,都有两个可能:先遇到店,或者先遇到花
   if(a>0)
     f(a-1,b,c*2); // 逢店加一倍
   if(b>0)
     f(a,b-1,c-1); // 遇花喝一斗
   if(a==0&&b==0&&c==1) //这个是满足要求的终止条件。没有店剩下,还剩一朵花和一斗酒
     sum=sum+1;
    return sum;
}
int main()
{
    f(5,9,2);
    cout<<sum<<endl;
}

70,037

社区成员

发帖
与我相关
我的任务
社区描述
C语言相关问题讨论
社区管理员
  • C语言
  • 花神庙码农
  • 架构师李肯
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧