蓝桥杯 骰子迷题

题目:

标题:骰子迷题
    小明参加了少年宫的一项趣味活动:每个小朋友发给一个空白的骰子(它的6个面是空白的,没有数字),要小朋友自己设计每个面写哪个数字。但有如下要求:
    1. 每个面只能填写 0 至 8 中的某一个数字。
    2. 不同面可以填写同样的数字,但6个面总和必须等于24。
    填好后,小朋友可以用自己填写好数字的骰子向少年宫的两个机器人挑战----玩掷骰子游戏。规则如下:
    三方同时掷出自己的骰子,如果出现任何相同的数字,则三方都不计分。
    如果三方数字都不同,则最小数字一方扣 1 分,最大数字一方加 1 分。
    小明看到了两个机器人手中的骰子分别是:
    0 0 0 8 8 8
    1 1 4 5 6 7
    请你替小明算一下,他如何填写,才能使自己得分的概率最大。
    请提交小明应该填写的6个数字,按升序排列,数字间用一个空格分开。
    如果认为有多个答案,提交字母序最小的那个方案。
    请严格按照格式,通过浏览器提交答案。
    注意:只提交一行内容,含有6个被空格分开的数字。不要写其它附加内容,比如:说明性的文字。


思路:这道题刚开始看好像有点难,如果用数学的方式求解的话,是有点不好做,坑就在这里。但是这是编程题,貌似没有暴力解决不了的问题。重新整理下思路,发现得分概率最大其实就等价于自己的骰子中,各个面的数字大于机器人1的骰子的数量的为x1,大于机器人2的骰子的数量为x2,概率P=SUM(x1[i]*x2[i])/6*6*6 (1<=i<=6). 其实就是求SUM(x1[i]*x2[i])的最大值。


#include
using namespace std;

int a[6]={0,0,0,8,8,8};
int b[6]={1,1,4,5,6,7};
int c[6]={0};
int temp[6]={0};
int MAX=0;

void count()
{
   int m=0,x1=0,x2=0;
   for(int i=0;i<6;i++){
     x1=x2=0;
   	 for(int j=0;j<6;j++){
   	 	if(c[i]>a[j])
   	 		x1++;
   	 	else
   	 		break;
   	 }
   	 
   	 for(int j=0;j<6;j++){
   	 	if(c[i]>b[j])
   	 		x2++;
   	 	else
   	 		break;
   	 }
   	 
   	 m+=x1*x2;
   }
   if(m>MAX){
   	for(int i=0;i<6;i++){
   		temp[i]=c[i];
   	}
   	MAX=m;
   }
}

void dfs(int n,int cur,int sum)
{
	if(sum>24) return;
	if(n==6)
	{
		if(sum==24){//计算概率 
			count();
		}
		return;
	}
	for(int i=cur;i<9;i++)
	{
		if((5-n)*8>=24-sum-i) //剪枝 
		{
			c[n]=i;
			dfs(n+1,i,sum+i);	
			c[n]=0;
		}
	}
	
}

int main()
{
	dfs(0,0,0);
	
	for(int i=0;i<6;i++)
		cout<





你可能感兴趣的:(蓝桥杯)