题解
【入门】恐龙园买玩具?
1 条题解
-
0
解题思路
题目里有 4 个条件,先看清楚
小明要买两种恐龙玩具:
- 霸王龙:每只 x 元
- 三角龙:每只 y 元
他一共带了 n 元,买玩具要满足这 4 个条件:
- 两种都要买:霸王龙至少 1 只,三角龙也至少 1 只;
- 霸王龙数量 >= 三角龙数量:霸王龙不能买得比三角龙少;
- 总数 >= 5:两种恐龙加起来至少 5 只,才够分给 5 位朋友;
- 不能有钱剩下:花的钱要刚好等于 n 元。
把所有满足条件的购买方案都输出出来。
核心思路:枚举霸王龙的数量 a
我们设霸王龙的数量是 a,三角龙的数量是 b。
小明一共带了 n 元,买了 a 只霸王龙(每只 x 元)之后,剩下的钱是:
n - a * x如果剩下的钱能刚好买整数只三角龙,也就是 能被 y 整除,那么:
b = (n - a * x) / y这样第 4 个条件(不剩钱)就自动满足了——因为剩下的钱全部拿去买三角龙了。
所以我们只要 从小到大枚举 a(a 从 1 开始,且 a*x 不能超过总钱数 n),用公式算出 b,再检查剩下的 3 个条件:
- b >= 1:三角龙也要买;
- a >= b:霸王龙数量不少于三角龙数量;
- a + b >= 5:总数够分给 5 位朋友。
全都满足,就输出 a 和 b。
用样例演示一遍(n=100,x=10,y=5)
- a = 1:1*10=10,剩 90,90/5=18,b=18。但 a>=b?1>=18 不成立,跳过。
- a = 2:2*10=20,剩 80,80/5=16,b=16。2>=16 不成立,跳过。
- …… a 太小的时候,三角龙会买得比霸王龙多,都不满足。
- a = 7:7*10=70,剩 30,30/5=6,b=6。7>=6 成立,7+6=13>=5 成立,输出
7 6 - a = 8:8*10=80,剩 20,20/5=4,b=4。8>=4 成立,8+4=12>=5 成立,输出
8 4 - a = 9:9*10=90,剩 10,10/5=2,b=2。9>=2 成立,9+2=11>=5 成立,输出
9 2 - a = 10:10*10=100,剩 0,0/5=0,b=0。b>=1 不成立,跳过。
所以样例输出的三行就是:
7 6 8 4 9 2正好和题目要求一模一样!因为 a 是从小到大枚举的:先输出的方案霸王龙少,后输出的方案霸王龙多,正好满足题目要求的"霸王龙数量从少到多",顺序天然正确,不用再排序。
再试一组数据(n=60,x=10,y=5)
- a = 4:410=40,剩 20,20/5=4,b=4。4>=4 成立,4+4=8>=5 成立,输出
4 4(410+4*5=60 刚好不剩钱) - a = 5:5*10=50,剩 10,10/5=2,b=2。5>=2 成立,5+2=7>=5 成立,输出
5 2 - a = 6:6*10=60,剩 0,b=0,b>=1 不成立,跳过。
输出就是
4 4和5 2,用同样的方法核验:每一行都刚好花光 60 元。小结
这种"枚举一种数量,用公式算出另一种数量,再逐个检查条件"的做法,叫做 枚举 + 判断。枚举 a 的时候就保证了"不剩钱"和"输出顺序",后面只需要判断 3 个条件,非常简单,也不容易出错。
参考代码
// 包含输入输出需要用到的头文件 #include <iostream> using namespace std; int main() { // n 表示一共带的钱,x 表示一只霸王龙的价钱,y 表示一只三角龙的价钱 int n, x, y; cin >> n >> x >> y; // 枚举霸王龙的数量 a // a 从 1 开始(霸王龙至少要买 1 只),并且 a*x 不能超过总钱数 n for (int a = 1; a * x <= n; a++) { // 买完 a 只霸王龙后剩下的钱 int rest = n - a * x; // 剩下的钱必须能被三角龙的单价 y 整除,才能做到不剩钱 if (rest % y != 0) { continue; } // 三角龙的数量 b int b = rest / y; // 条件1:三角龙也要买(b >= 1) // 条件2:霸王龙数量不少于三角龙数量(a >= b) // 条件3:总数够分给 5 位朋友(a + b >= 5) if (b >= 1 && a >= b && a + b >= 5) { // 先输出霸王龙数量 a,再输出三角龙数量 b,中间用空格隔开 cout << a << " " << b << endl; } } return 0; }复杂度分析
- 时间复杂度:O(n/x)。我们只用了一层 for 循环,枚举 a 从 1 到 n/x,循环次数大约是 n/x 次。题目里 n<=999,规模很小,就算 x=1 最多也就循环几百次,运行非常快。
- 空间复杂度:O(1)。我们只用了 n、x、y、a、b、rest 这几个 int 变量,没有使用数组等额外空间。
- 1