天平称重

        today,这道水题的大意为:输入三个整数数a,b(a≠b, a≤10000, b≤10000,c≤50000)(都可以无限取)和c,使a,b通过加或减得到c,输出最少要几个a,b,用n,m表示,且n+m要最小(这题每次有k组数据,以输入0 0 0为结束);

     当我看到这道题时,第一个思路是模拟,就是n,m初值附0,然后枚举,这是个思路,代码如下:

​
#include<bits/stdc++.h>
using namespace std;
int a,b,c,d,minn=100000,minnn=1000000,x,y;
int main()
{
	while(1)
    {
		cin>>a>>b>>c;
		if(a==0||b==0||c==0) break;
		for(int i=0;i<=10000;i++)//枚举暴力
		    for(int j=0;j<=10000;j++)//暴力枚举
		        if(a*i+b*j==c||a*i-b*j==c||b*j-a*i==c)//判断,若满足,记录状态
		        {
		            if(i+j<minn)
		            {
		                minn=i+j;
		                if(a*i+b*j<minnn)//判断是否最优
		                x=i;y=j;break;
                    }
	                x=i;
	                y=j;
		            d=0;
                }
    }
    cout<<x<<' '<<y;
}

​

       显然,从0枚举到10000已经是10^8还要计算,肯定会爆的。

       然后,发现枚举n,m不行,那就可以反过来,让a,b翻倍,在相减得到c,这个方法应该是可行的,但我还是优化了一下,可以让a或b不变,另一个数翻倍,再减去c,看看是否满足条件,不过这样有两种情况,会有点累。但一时疏懒的我还是这样敲了:

#include<bits/stdc++.h>
using namespace std;
int main()
{ 
    int a,b,c;
    while(1)
    {
    	cin>>a>>b>>c;
    	int aa=0,bb=b,ana=0,anb=0,aaa,bbb,aa1,bb1;
    	if(a==0&&b==0&&c==0) return 0;
		while(1)//这里让aa即a翻倍
		{
			if((aa-c)%bb==0)//判断是否满足条件
			{aaa=ana,bbb=max((aa-c)/bb,-(aa-c)/bb)/*记录状态并更新*/;break;}
			aa+=a,ana++;//翻倍
		}
        /*下同*/
		aa=a,bb=0;
		while(1)
		{
			if((bb-c)%aa==0)
			{aa1=max((bb-c)/aa,-(bb-c)/aa),bb1=anb;break;}
			bb+=b;anb++;
		}
		if(aaa+bbb>aa1+bb1)/*找最优*/ cout<<aa1<<' '<<bb1<<endl;
		else cout<<aaa<<' '<<bbb<<endl;
	}
} 

      这代码看起来很low,确实有很多可以改进的地方,比如变量名就很low,还有附初值时可以简单判断,然后附适当的值,相当于减少计算量,如果您是大佬,也可以帮在下把两种情况压成一种情况。不过,我还是0ms的时间A的,so就不想优化了。

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值