小学期 BlueSky学长与友人帐

Description

这天,夏目和猫咪老师去七迁屋买老师最喜欢吃的馒头了,就把强大的友人帐拜托给了BlueSky学长。突然,一只带着白色面具的庞大妖怪出现在学长面前,用阴森恐怖的声音说如果拿不到自己的名字就要吃掉BlueSky学长。BlueSky学长赶忙掏出友人帐摆在面前,学着夏目的样子双手合十口中念念有词,友人帐竟然真的翻到了写有妖怪名字的那一页,不一样的是,友人帐上出现了四个数字,BlueSky学长可以任意使用加减乘除和括号,只要最终得出24,就能成功撕下这一页把名字还给妖怪,否则妖怪就要吃掉BlueSky学长了。当然,以BlueSky学长的智商,只要有可行方案,学长就一定可以计算算出来的,现在只需要请请机智的你判断一下,BlueSky学长最终能不能成功还给妖怪名字逃脱被吃的命运。


Input

多组用例,每组用例给出4个小于10的正整数a, b, c, d,最终以0 0 0 0结束。最后一行不需要处理。

Output

对于每组用例输出一行,如果BlueSky学长能成功归还名字,输出"YES",否则输出"NO“。

测试用例:

输入:

5 5 5 1
1 1 4 2
0 0 0 0

输出:

YES
NO

题解:

24点问题,网上很多解法,在此说一种

由于“+” “×”满足运算符两边数字可以交换而“-” “/”不满足,联想到MATLAB中有“\”即左除运算,我们也可以再定义两种运算“^”和“%”,则a^b=b-a,a%b=b/a(其他符号也行),这样就只有两种加括号方式:

(1)(((a@b)@c)@d)

(2)((a@b)@(c@d))

数字位共4!=24种,符号有6^3=216种,两种加括号方式,共24*216*2 枚举即可。

也可以搜索写。

代码:

#include<stdio.h>
#include<string.h>
float a[4];
char cc[6]={'+','-','*','/','^','%'};
int inf=0x3f3f3f3f;
float fun1(float a,float b,char ch)
{
	if(ch=='+') return a+b;
	if(ch=='-') return a-b;
	if(ch=='*') return a*b;
	if(ch=='/')
	{
		if(b==0) return inf;
		else return a/b;
	}
	if(ch=='^') return b-a;
	if(ch=='%')
	{
		if(a==0) return inf;
		else return b/a;
	}
}
int check()
{
	int i,j,k,l,m,n,o;
	float ans,ans1,ans2,ans3;
	for(i=0;i<4;i++)
	{
		for(j=0;j<4;j++)
		{
			if(j==i) continue;
			for(k=0;k<4;k++)
			{
				if(k==i||k==j) continue;
				for(l=0;l<4;l++)
				{
					if(l==i||l==j||l==k) continue;
					//if(i==1&&j==2&&k==0&&l==3) printf("%f %f %f %f\n",a[i],a[j],a[k],a[l]);
					for(m=0;m<6;m++)
					{
						ans=fun1(a[i],a[j],cc[m]);
						//if(i==1&&j==2&&k==0&&l==3&&cc[m]=='+') printf("%f\n",ans);
						for(n=0;n<6;n++)
						{
							//if(a[k]==2&&cc[m]=='+'&&cc[n]=='*') printf("%f %f\n",a[k],ans);
							ans1=fun1(ans,a[k],cc[n]);
							//if(a[k]==2&&cc[m]=='+'&&cc[n]=='*') printf("%f %f\n",a[k],ans);
							for(o=0;o<6;o++)
							{
								ans2=fun1(ans1,a[l],cc[o]);
								//printf("%f %c %f %c %f %c %f = %f\n",a[i],cc[m],a[j],cc[n],a[k],cc[o],a[l],ans2);
								if(ans2<=24.1&&ans2>=23.9) return 1;
								//if(a[i]==1&&cc[m]=='/'&&cc[n]=='^'&&cc[o]=='*') printf("%f",ans2);
							}
						}
					}
					
					for(m=0;m<6;m++)
					{
						ans1=fun1(a[i],a[j],cc[m]);
						for(n=0;n<6;n++)
						{
							ans2=fun1(a[k],a[l],cc[n]);
							for(o=0;o<6;o++)
							{
								ans=fun1(ans1,ans2,cc[o]);
								if(ans<=24.1&&ans>=23.9) return 1;
							}
						}
					}
					
				} 
			}
		}
	}
	return 0;
}
int main()
{
	while(scanf("%f%f%f%f",&a[0],&a[1],&a[2],&a[3]),a[0]!=0||a[1]!=0||a[2]!=0||a[3]!=0){
		int flag=check();
		if(flag==1) printf("YES\n");
		else printf("NO\n");
	}
	return 0;
} 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值