A.比大小
解题思路
已知
- 芭芭拉比迪奥娜大;
- 可莉比芭芭拉小;
- 可莉比迪奥娜小。
容易得到:芭芭拉大于迪奥娜大于可莉
直接输出即可
AC_Code
#include <stdio.h>
int main() {
puts("芭芭拉");
puts("可莉");
return 0;
}
B.两艘船
解题思路
设 为船中货物的质量差。我们的目标是使
等于
。请注意,只要运一次,我们就可以把
到
范围内的任何数字相加。因此,问题的答案将是
。
AC_Code
#include <stdlib.h>
#include <stdio.h>
#include <math.h>
int main() {
int t;
scanf("%d", &t);
while (t--) {
float a, b, c;
int ans;
scanf("%f %f %f", &a, &b, &c);
int tem = abs(a - b);
int res = tem / (2 * c);
if(res * (2 * c) == tem)
printf("%d\n", res);
else
printf("%d\n", res + 1);
}
return 0;
}
C.活动
解题思路
反向思考,如果有 个人,在能确定毒药位置的情况下所允许的最多的水的杯数是多少?
我们把 个人排成一列,看作一个
位的二进制整数,可以发现有
种不同的方案去喝水。
当 时,可以确定
杯水中毒药的位置。
转化一下,就有
AC_Code
#include <stdio.h>
#include <math.h>
int main() {
int n; scanf("%d", &n);
if(n == 1)
{
printf("%d\n", 0);
}
else
{
int res = log2(n + 1);
if (pow(2, res) < n) res ++;
printf("%d\n", res);
}
return 0;
}
D.理想点
解题思路
首先,让我们删除所有不覆盖点 的线段(因为它们会增加函数
在
以外的点上的值)。如果没有剩余的线段,那么答案就是 "否"。否则,所有线段都覆盖了点
。剩下的工作就是检查点
是否是唯一一个被所有线段覆盖的点。需要注意的是,删除任何剩余的线段都是没有意义的,因为如果有几个点的最大值是
,那么删除线段只会增加它们的数量。
要检查最大值为 的点的数量,可以从
到
遍历
,然后计算
,因为问题中的线段数量很少。更快捷的方法是检查所有线段交集的大小。交点的左边界是
,右边界是
;如果是
,那么点
是理想点,否则不是。
AC_Code
#include <stdio.h>
#include <math.h>
int main() {
int t;
scanf("%d", &t);
while (t--) {
int n, k;
scanf("%d %d", &n, &k);
int L = 0, R = 55;
while (n--) {
int l, r;
scanf("%d %d", &l, &r);
if (l <= k && k <= r)
{
L = (L > l)? L : l;
R = (R < r)? R : r;
}
}
if(L == R) puts("YES");
else puts("NO");
}
}
E.交易
解题思路
当 时,小宇可以选择通过多次交易来赚取银币, 所以只需完成游戏中的一个任务即可。
当 时,小宇只能通过完成游戏中的任务的方式赚钱,所以所需完成的最小任务数为
AC_Code
#include <stdio.h>
#include <math.h>
int main() {
int t;
scanf("%d", &t);
while(t -- )
{
int n, a, b;
scanf("%d %d %d", &n, &a, &b);
if(a > b)
{
printf("1\n");
}
else
{
if((int)(n / a) * a == n) printf("%d\n", n / a);
else printf("%d\n", n / a + 1);
}
}
return 0;
}
F.烦恼
解题思路
给定:
已知 ,
,
,求
,
。
拆一下上面的式子,得:
根据第一个式子,得到
。
代入第二个式子:
因为 ,
,
已知,
,
,
,算出判别式:
代入算出 的公式:
直接计算即可。
AC_Code
#include <stdio.h>
#include <math.h>
int main() {
int t; scanf("%d", &t);
while(t -- )
{
long long n, e, d;
scanf("%lld %lld %lld", &n, &e, &d);
long long m = n - e * d + 2;
long long delta = m * m - 4 * n;
long long q = sqrt(delta);
if(delta < 0 || q * q != delta || (m + q) % 2) {
puts("NO");
continue;
}
q = (m + q) / 2;
long long p = n / q;
if(p * q != n || p < 0 || q < 0) {
puts("NO");
continue;
}
printf("%lld %lld\n", p, q);
}
return 0;
}
G.行走大师
解题思路
提示 1: 的值总是不递减的,而
的值总是不递增的。
当且仅当 和
时,才有可能从
移动到
,因为
的值总是不递减的,而
的值总是不递增的。
如果可能,答案就是 。一种可能的方法是
。
另一种理解方式是如果可以从 移动到
,那么
总是一条有效的路径。因此首先假设
和
,那么答案只取决于
和
。
AC_Code
#include <stdlib.h>
#include <stdio.h>
#include <math.h>
int main()
{
int T;
scanf("%d", &T);
while(T -- )
{
int a, b, c, d;
scanf("%d %d %d %d", &a, &b, &c, &d);
if(b <= d && c <= a + d - b) {
printf("%d\n", (d - b) + (a + d - b - c));
} else {
puts("-1");
}
}
return 0;
}