CF教育场 104 解题补题报告

A题 Arena (签到)

现在有 \(n\) 个英雄,第 \(i\) 个英雄的初始等级为 \(a_i\)

两个英雄可以战斗(不止一次),等级高的那个将会获胜,并且等级升一级(如果两个等级一样,那么就是平局,等级不变化)。如果一个英雄等级高于所有别的英雄,那么他就会成为王者。

问,有多少英雄有可能成为王者?

\(2\leq n \leq 100,1\leq a_i\leq 100\)

这题一开始给我整懵了,后来才发现是一个白给题

很显然,对于那些等级最低的英雄(们),他们不可能赢(至多平局),等级不可能提升到比别的英雄高

其他的英雄,只要逮着这些等级最低的菜鸡刷经验,那么就可以把等级一路刷上去,然后成为王者

所以只要把数组里面的最小元素全筛掉,剩下的元素的个数就是答案了

#include<bits/stdc++.h>
using namespace std;
const int N = 110;
int n, a[N];
void solve()
{
    scanf("%d", &n);
    for (int i = 1; i <= n; ++i)
        scanf("%d", &a[i]);
    int Minv = 110;
    for (int i = 1; i <= n; ++i)
        Minv = min(Minv, a[i]);
    int ans = 0;
    for (int i = 1; i <= n; ++i)
        if (a[i] != Minv) ++ans;
    printf("%d\n", ans);
}

int main()
{
    int T;
    scanf("%d", &T);
    while (T--) solve();
    return 0;
}

B题 Cat Cycle

有两只猫 \(A\)\(B\),以及 \(n\) 个垫子。

按照时刻顺序,\(A\) 会坐在的垫子的编号分别是 \(n,n-1,...,3,2,1,n,n-1,...\) ,而 \(B\) 则是 \(1,2,3,...,n-1,n,1,2,3,...\)

如果 \(A\)\(B\) 产生冲突,那么优先遵循 \(A\) 的要求,并且此后 \(B\) 不会再去尝试坐在这个曾经产生冲突的垫子。

给定 \(k\),问 \(B\) 在时刻 \(k\) 会坐在哪个垫子上面?

\(2 \leq n \leq 10^9,1 \leq k \leq 10^9\)

不难发现, \(n\) 是偶数的时候,两只猫不会产生冲突,所以直接输出 \((k-1)\%n+1\) 即可。

\(n\) 是奇数就比较离谱了:并不是很会(逃

C题 Minimum Ties (思维,构造)

\(n\) 支队伍,两两之间打一场比赛,比赛会有两种情况:

  1. 平局,两队各得 \(1\)
  2. 出现胜负,胜者得 \(3\) 分,败者不得分

现在尝试安排一种比赛安排(包括他们的胜负),可以使得最后所有队伍得分相同,并且平局数量最少,并且输出该方案

\(2 \leq n \leq 100\)

我们不妨记有 \(k\) 局具有明确胜负,\(\frac{n(n-1)}{2}-k\) 局是平局,最后总得分则是 \(3k+2(\frac{n(n-1)}{2}-k)=n(n-1)+k\)

所有人得分相同,那么 \(k\) 必须可以被 \(n\) 整除,且 \(k\) 的值越大越好,那么 \(0 \leq \frac{k}{n} \leq \frac{n-1}{2}\) 。换言之,\(\frac{k}{n}\) 是不大于 \(\frac{n-1}{2}\) 的最大值。

那么很显然: \(n\) 为奇数时,没有平局;\(n\) 为偶数时,恰好有 \(\frac{n}{2}\) 局平局。

代码略(其实是我不会

D题 Pythagorean Triples (数学)

给定正整数 \(n\),问有多少三元组 \((a,b,c)\) 同时满足 \(a^2+b^2=c^2,a^2=b+c\)

\(1 \leq a \leq b \leq c \leq n\)

不难发现,\(c^2-b^2=(c+b)(c-b)=b+c\) ,故 \(c=b+1,a^2=2b+1\)

因为 \(a \leq b\),不难证明 \(b \geq 4\)

那么问题就显然了:有多少个 \(b\) ,满足 \(4 \leq b < n\) ,且 \(2b+1\) 是完全平方数?

打表发现,当且仅当 \(b=2k(k+1)\) 时成立,那么照着写就完事了。

#include<bits/stdc++.h>
using namespace std;
#define LL long long
void solve()
{
    LL n, k;
    scanf("%lld", &n);
    for (k = 1; 2*k*(k+1) < n; ++k);
    printf("%lld\n", k-1);
}

int main()
{
    int T;
    scanf("%d", &T);
    while (T--) solve();
    return 0;
}

下面给出数学证明:显然 \(a\) 是奇数,所以不妨设 \(a=2k+1\) ,所以 \(b=\frac{(2k+1)^2-1}{2}=2k(k+1)\) (逃

posted @ 2021-02-16 19:58  cyhforlight  阅读(75)  评论(0编辑  收藏  举报