题目
输入样例:
4 7
输出样例:
17
思路
一个字,猜。
一开始不知道怎么做的时候,想要暴力枚举对于特定的包装n, m,最大不能买到的数量maxValue是多少,然后观察性质做优化。那么怎么确定枚举结果是否正确呢?
题目说“一定有解”,那么怎样的数据才有解?当gcd(n, m) 大于1,比如gcd(n, m) = 2,只要糖果的数量是2的倍数,那么这个数就能用n和m包装完,而糖果的数量不是2的倍数,就不能用n和m包装完,因此不存在最大不能买到的数量。而当gcd(n, m) 等于1时,必定有最大不能买到的数量。证明可以参考这篇文章:证明。
暴力代码如下:
#include<bits/stdc++.h>
using namespace std;
bool dfs(int d, int p, int q)
{
if (d == 0) return true;
else if (d < 0) return false;
if(dfs(d - p, p, q))return true;
if(dfs(d - q, p, q))return true;
return false;
}
int main()
{
int n, m;
cin >> n >> m;
/*
求对于特定的包装n, m,最大不能买到的数量maxValue;先假定对任意的n, m,
最大不能买的数不超过1000,如果结果maxValue超过1000,再扩大i的范围
*/
int maxValue = 0;
for (int i = 1; i <= 1000; i ++)
{
//若i不能买到
if(!dfs(i, n, m))maxValue = i;
}
cout << maxValue;
return 0;
}
以下是计算的一些样例:
//样例1
n m res
2 7 5
3 7 11
4 7 17
5 7 23
//每当n加1,那么res就加6,如果建立n和res的等式,res应该是n的6倍。那么有res = 6n + x;加上x是为了//让等式成立,代入得x = -7
res = 6n - 7
//结果和上面类似
//样例2
n m res
2 5 3
3 5 7
4 5 11
res = 4n - 5
.
.
.
//猜公式
res = (m - 1)n - m
代码
#include<bits/stdc++.h>
using namespace std;
int main()
{
int n, m;
cin >> n >> m;
cout << (m - 1) * n - m;
return 0;
}