鬼谷子的钱袋-rqnoj-228

题目:

鬼谷子非常聪明,正因为这样,他非常繁忙,经常有各诸侯车的特派员前来向他咨询时政。有一天,他在咸阳游历的时候,朋友告诉他在咸阳最大的拍卖行(聚宝商行)将要举行一场拍卖会,其中有一件宝物引起了他极大的兴趣,那就是无字天书。但是,他的行程安

排得很满,他他已经买好了去邯郸的长途马车标,不巧的是出发时间是在拍卖会快要结束的时候。于是,他决定事先做好准备,将自己的金币数好并用一个个的小钱袋装好,以便在他现有金币的支付能力下,任何数目的金币他都能用这些封闭好的小钱的组合来付账。鬼谷子也是一个非常节俭的人,他想方设法使自己在满足上述要求的前提下,所用的钱袋数最少,并且不有两个钱袋装有相同的大于1的金币数。假设他有m个金币,你能猜到他会用多少个钱袋,并且每个钱袋装多少个金币吗?

   

  2进制是宝!!!

     相传是最水的一道省选题,的确有点水,连我这种才学4个月的蒟蒻都会做。

     任何数都可以转化成2进制,并且只有2进制的数转化为十进制时每位的权值乘一,而其他的进制不行,而这个特性恰好满足题意,也就是说任何一个数都可以有2的幂相加得到。于是,第一种方法就出来了:本人语文不好,只有边举例边讲解,拿10来举例,把10分解成2的幂相加,1+2+4=7,再加一个8和就超过十了,所以不能算上8,此时还剩个3,因为已经有1,2,4了,4代表的是2进制“千位”,所以二进制数“111”以内即7以内的数都可以表示出来了,因为还剩3,所以8,9,10也表示出来了。这种方法就是从最小的2的幂往上找,最后剩下的那个数如果不是2的幂,用一个钱袋装起来就是了,即钱袋总数log2(n)+1,如果最后剩的这个数恰好是某个2的幂,只用与这个幂一个+1另一个-1就对 了。2进制是最优解。

      第二种解法:不断/2,这样求出的方案不是最优,但可以A,并且代码好写。

      以下给出第二解法的代码。

#include<cstdio>
void wc(int n,int m)
{
	if(n==1)printf("%d\n",m+1);
	else wc(n/2,m+1);
	printf("%d ",n-n/2);
}
int main()
{
	int n;
	scanf("%d",&n);
	wc(n,0);
	return 0;
}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值