不多bb,线上链接:https://www.luogu.com.cn/problem/P1618
放题干:
开始分析:
刚看到题目,我们可能会有一个简单粗暴的想法:就是,我能不能从九个数里面拿三个数字给X,拿另外三个数给Y,然后最后三个数给Z,最后我们判断一下这个X:Y:Z 满 A:B:C。这个方法理论上是行得通的,我们需要借助一个 stl 函数 next_permutation(start,end) 头文件是algorithm
这个函数的用处是随机排列一个数组,那我们可以用它随机排列1~9里的数字,前三个给X以此类推。
but.....我们今天讲的重点是暴力枚举
暴力枚举,就是通过枚举所有的情况来得到答案。最简单的做法是三个循环,x从123开始,到987结束,y从123开始,到987结束......
那么我们算一下 大概是循环 864*864*864*3*10 约为1e11
那么我们优雅地给它优化一下:
可以发现,其实不需要枚举 x,y,z;
只需要枚举一个数,然后通过比例来查找y,z是否存在就行了;
这样循环的次数大概是 (987-123)*3*10 == 1e5
大概思路:
枚举x,,123<=x<=987,然后查找 在A:B:C的比例下,y,z是否存在
如果存在,赋值y,z。
然后搞一个计数排序统计x,y,z各个位数的出现次数。
最后输出就行了。
上代码!!!!
typedef long long LL;
int flag[20];
void Flag(int x)
{
int temp = x;
while (temp)
{
flag[temp % 10] = 1;
temp /= 10;
}
}
bool check(int a, int b, int c)
{
memset(flag, 0, sizeof(flag));
Flag(a); Flag(b); Flag(c);
for (int i = 1; i <= 9; i++)
if (!flag[i])return false;
return true;
}
int main()
{
LL a, b, c, A, B, C,ans=0;
cin >> A >> B >> C;//A<B<C
if (A != 0) {
for (a = 123; a <= 987; a++)
{
if ((a * B) % A or (a * C) % A) continue;
b = (a * B) / A;
c = (a * C) / A;
if (b <= 987 and b >= 123 and c <= 987 and c >= 123)// b,c是三位数
{
if (check(a, b, c))
{
cout << a << ' ' << b << ' ' << c << endl;
ans++;
}
}
}
if (ans == 0)cout << "No!!!";
}
else cout << "No!!!";
}
最后注意,A一定不能为0,所以我们还要分类讨论一下。