蓝桥杯-第九届决赛——海盗与金币

海盗与金币

结果填空(满分29分)

标题:海盗与金币

12名海盗在一个小岛上发现了大量的金币,后统计一共有将近5万枚。

登上小岛是在夜里,天气又不好。由于各种原因,有的海盗偷拿了很多,有的拿了很少。

后来为了“均贫富”,头目提出一个很奇怪的方案:

每名海盗都把自己拿到的金币放在桌上。然后开始一个游戏。

金币最多的海盗要拿出自己的金币来补偿其他人。

补偿的额度为正好使被补偿人的金币数目翻番(即变为原来的2倍)。

游戏要一直进行下去,直到无法完成。

(当金币数最多的不只一个人或最多金币的人持有金币数不够补偿他人的)

游戏就这样紧张地进行了,一直进行了12轮,恰好每人都“放血”一次,

更离奇的是,刚好在第12轮后,每个人的金币数居然都相等了!! 这难道是天意吗?

请你计算,游戏开始前,所有海盗的初始金币数目,从小到大排列,中间有一个空格分开。

答案形如:

8 15 29 58 110 ...

当然,这个不是正确答案。

注意:需要提交的是一行空格分开的整数,不要提交任何多余的内容。

分隔符要用一个西文的空格,不要用其它符号(比如逗号,中文符号等)

 

答案:13 25 49 97 193 385 769 1537 3073 6145 12289 24577

思路: 这道题思考了好久,由题意可知:有12名海盗,将近5万枚金币。

一直进行了12轮,恰好每人都“放血”一次,满足条件了就按小到大输出。

其它解析在代码中。

public class Main {

	public static void main(String[] args) {
		
		int [] b =new int [12];//12名海盗
		
		/**
		 * 有将近5万枚硬币可知范围
		 * 因为在第12轮后 每个人的金币数都相等了 所以12个人总的金币数 应该是12的倍数
		 */
		for(int i=12;i<50000;i+=12){
			for(int j=0;j<12;j++){//12轮后的结果
				b[j] = i/12;
			}
			dfs(b,11,i);//最后一个是最大的
		}
		
	}
	/**
	 * b是这12个人手中的金币数
	 * MaxIn是当前金币最多的那个人
	 * sum为总的金币数
	 */
	public static void dfs(int [] b,int MaxIn,int sum){
		if(MaxIn<0){
			for(int i=11;i>=0;i--){
				System.out.print(b[i]+" ");
			}
//			System.out.println("*"+sum);
			return;
		}
		int count = 0;
		for(int i=0;i<12;i++){
			if(i==MaxIn){
				continue;
			}else{
				if(b[i]%2!=0){
					return;
				}else{
					b[i]=b[i]/2;
					count+=b[i];
				}
			}
		}
		b[MaxIn] = sum-count;
		dfs(b,MaxIn-1,sum);
	}
	
}
//13 25 49 97 193 385 769 1537 3073 6145 12289 24577

 

评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

萤火的微亮

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值