AtCoder Weekday Contest 0006 Beta题解(AWC 0006 Beta A-E)

A - Target Shooting Game

【题目来源】

AtCoder:A - Target Shooting Game

【题目描述】

Takahashi is playing a target shooting game at a summer festival.
高桥正在夏祭上玩一个射击游戏。

In front of Takahashi, \(N\) balls are prepared. Each ball has a different weight, and the weight of the \(i\)-th ball is \(D_i\). When Takahashi throws a ball, it flies a distance proportional to its weight. Specifically, when a ball of weight \(D\) is thrown, it flies exactly a distance of \(D\).
在高桥面前,准备了 \(N\) 个球。每个球的重量不同,且第 \(i\) 个球的重量为 \(D_i\)。当高桥扔出一个球时,它会飞出一段与其重量成比例的距离。具体而言,当一个重量为 \(D\) 的球被抛出时,它恰好飞出距离 \(D\)

A target is placed at distance \(L\) from Takahashi. The target has some width, and a ball is considered to have hit the target if it lands at a distance from Takahashi that is at least \(L - W\) and at most \(L + W\).
一个靶子被放置在高桥前方距离 \(L\) 的位置。靶子具有一定的宽度,如果一个球落地点与高桥的距离至少为 \(L-W\) 且至多为 \(L+W\),则认为该球命中了靶子。

When Takahashi throws all \(N\) balls one by one, find the number of balls that hit the target.
当高桥依次扔出所有 \(N\) 个球时,求命中靶子的球数。

【输入】

\(N\) \(L\) \(W\)
\(D_1\) \(D_2\) \(\ldots\) \(D_N\)

  • The first line contains \(N\) representing the number of balls, \(L\) representing the distance to the target, and \(W\) representing the value related to the target's width, separated by spaces.
  • The second line contains \(D_1, D_2, \ldots, D_N\) representing the weight of each ball, separated by spaces.

【输出】

Output the number of balls that hit the target in one line.

【输入样例】

5 10 3
5 8 10 13 15

【输出样例】

3

【解题思路】

image

【代码详解】

#include <bits/stdc++.h>
using namespace std;
int n, l, w, ans;  // n: 数据个数,l: 中心值,w: 允许的偏差,ans: 符合条件的数量

int main()
{
    cin >> n >> l >> w;  // 读入数据个数、中心值和允许偏差
    
    for (int i = 1; i <= n; i++)
    {
        int d; 
        cin >> d;  // 读入当前数据
        
        // 检查当前数据是否在[l-w, l+w]范围内
        if (d >= l - w && d <= l + w)
        {
            ans++;  // 如果在范围内,计数器加1
        }
    }
    
    cout << ans << endl;  // 输出符合条件的数量
    return 0;   
}

【运行结果】

5 10 3
5 8 10 13 15
3

B - Efficient Quests

【题目来源】

AtCoder:B - Efficient Quests

【题目描述】

Takahashi is playing an RPG game. The game has \(N\) quests, and the \(i\)-th quest \((1 \leq i \leq N)\) has a stamina cost of \(D_i\) and an experience reward of \(R_i\). For each quest, he can choose either not to clear it or to clear it exactly once.
高桥正在玩一款 RPG 游戏。游戏中有 \(N\) 个任务,第 \(i\) 个任务(\(1 ≤ i ≤ N\))的体力消耗为 \(D_i\),经验值奖励为 \(R_i\)。对于每个任务,他可以选择不清除,或者恰好清除一次。

Takahashi has a playstyle of "only clearing efficient quests." For Takahashi, an efficient quest is one whose experience reward is at least \(K\) times its stamina cost, that is, a quest satisfying \(R_i \geq K \times D_i\). Here, \(K\) is the efficiency threshold multiplier set by Takahashi.
高桥的玩法是"只清除高效任务"。对高桥而言,一个高效任务是指其经验值奖励至少为体力消耗的 \(K\) 倍,即满足 \(R_i ≥ K × D_i\) 的任务。此处,\(K\) 是高桥设定的效率阈值倍数。

Following this playstyle, Takahashi clears all efficient quests and does not clear any other quests.
遵循这种玩法,高桥会清除所有高效任务,并且不清除任何其他任务。

Determine whether the total experience gained from the quests Takahashi clears following this playstyle is at least the target experience \(T\).
判断高桥遵循这种玩法所清除任务获得的总经验值是否至少达到目标经验值 \(T\)

【输入】

\(N\) \(K\) \(T\)
\(D_1\) \(R_1\)
\(D_2\) \(R_2\)
\(\vdots\)
\(D_N\) \(R_N\)

  • The first line contains the number of quests \(N\), the efficiency threshold multiplier \(K\), and the target experience \(T\), separated by spaces.
  • From the 2nd line to the \((N + 1)\)-th line, the information for each quest is given.
  • The \((1 + i)\)-th line contains the stamina cost \(D_i\) and the experience reward \(R_i\) of the \(i\)-th quest, separated by spaces.

【输出】

If the total experience gained when Takahashi clears all efficient quests is at least the target experience \(T\), print Yes; otherwise, print No.

【输入样例】

3 2 100
10 30
5 15
8 20

【输出样例】

No

【解题思路】

image

【代码详解】

#include <bits/stdc++.h>
using namespace std;
#define int long long
int n, k, t, ans;  // n: 数据组数,k: 阈值系数,t: 目标值,ans: 满足条件的奖励总和

signed main()
{
    cin >> n >> k >> t;  // 读入数据组数、阈值系数和目标值
    
    for (int i = 1; i <= n; i++)
    {
        int d, r;  // d: 距离/次数,r: 奖励
        cin >> d >> r;  // 读入距离/次数和奖励
        
        // 如果奖励大于等于k倍的距离/次数
        if (r >= k * d)
        {
            ans += r;  // 累加奖励
        }
    }
    
    // 判断累计奖励是否达到目标值
    if (ans >= t)
    {
        cout << "Yes" << endl;
    }
    else
    {
        cout << "No" << endl;
    }
    return 0;
}

【运行结果】

3 2 100
10 30
5 15
8 20
No

C - Air Conditioner Temperature Adjustment

【题目来源】

AtCoder:C - Air Conditioner Temperature Adjustment

【题目描述】

Takahashi is the building manager of an office building. On a hot summer day, the air conditioner in each room has broken down, causing the room temperatures to rise too high.
高桥是一栋办公楼的物业经理。在一个炎热的夏日,每个房间的空调都发生故障,导致室内温度过高。

The building has \(N\) rooms, and the current temperature of room \(i\) \((1 \leq i \leq N)\) is \(T_i\) degrees. To ensure employees can work comfortably, the temperature of every room must be brought to at most the target temperature of \(M\) degrees.
该楼有 \(N\) 个房间,房间 \(i\)\(1 ≤ i ≤ N\))的当前温度为 \(T_i\) 度。为确保员工能舒适工作,必须将每个房间的温度降至最多为目标温度 \(M\) 度。

Takahashi can use as many cooling packs as needed. Using \(1\) cooling pack lowers the temperature of one chosen room by exactly \(D\) degrees. A cooling pack cannot be used partially; each pack always lowers the temperature by exactly \(D\) degrees. Multiple cooling packs can be used on the same room, and it is acceptable if a room's temperature drops well below \(M\) degrees or even becomes negative as a result.
高桥可以根据需要使用任意数量的冷却包。使用 \(1\) 个冷却包可将选定房间的温度恰好降低 \(D\) 度。冷却包不能部分使用;每个冷却包总是恰好降低温度 \(D\) 度。可以在同一房间使用多个冷却包,并且允许房间温度因此远低于 \(M\) 度甚至变为负数。

Find the minimum number of cooling packs needed to bring the temperature of every room to \(M\) degrees or below.
求将每个房间的温度降至 \(M\) 度或以下所需的最少冷却包数量。

【输入】

\(N\) \(M\) \(D\)
\(T_1\) \(T_2\) \(\ldots\) \(T_N\)

  • The first line contains three space-separated integers: \(N\) representing the number of rooms, \(M\) representing the target temperature, and \(D\) representing the temperature decrease per cooling pack.
  • The second line contains space-separated integers \(T_1, T_2, \ldots, T_N\) representing the current temperature of each room.

【输出】

Print a single integer on one line: the minimum number of cooling packs needed to bring the temperature of every room to \(M\) degrees or below.

【输入样例】

3 25 5
30 28 20

【输出样例】

2

【解题思路】

image

【代码详解】

#include <bits/stdc++.h>
using namespace std;
#define int long long
int n, m, d, ans;  // n: 数据个数,m: 阈值,d: 除数,ans: 结果

signed main()
{
    cin >> n >> m >> d;  // 读入数据个数、阈值和除数
    
    for (int i = 1; i <= n; i++)
    {
        int t; 
        cin >> t;  // 读入当前数据
        
        if (t <= m)  // 如果当前数据小于等于阈值,跳过
        {
            continue;
        }
        
        // 计算超过阈值部分需要多少个d
        // 公式:ceil((t - m) / d) 的整数计算技巧
        // ((t - m) + (d - 1)) / d
        ans += ((t - m) + (d - 1)) / d;
    }
    
    cout << ans << endl;  // 输出结果
    return 0;
}

【运行结果】

3 25 5
30 28 20
2

D - Placement of Security Guards

【题目来源】

AtCoder:D - Placement of Security Guards

【题目描述】

Takahashi is creating a security plan for a long corridor consisting of \(N\) sections (from section \(1\) to section \(N\)) arranged in a straight line. He must ensure that all sections are covered by security.
高桥正在为一条由 \(N\) 个区段(从区段 \(1\) 到区段 \(N\))组成的笔直长走廊制定安保计划。他必须确保所有区段都受到安保覆盖。

Takahashi has gathered \(M\) guard candidates. Each guard candidate \(i\) (\(1 \leq i \leq M\)) can cover a contiguous range from section \(L_i\) to section \(R_i\). That is, if guard candidate \(i\) is assigned, sections \(L_i, L_i + 1, \ldots, R_i\) are all covered.
高桥已招募了 \(M\) 名警卫候选人。每名警卫候选人 \(i\)\(1 ≤ i ≤ M\))可以覆盖从区段 \(L_i\) 到区段 \(R_i\) 的连续范围。也就是说,如果警卫候选人 \(i\) 被录用,则区段 \(L_i, L_i+1, …, R_i\) 都将被覆盖。

Takahashi wants all \(N\) sections to be covered. Specifically, he wants to select some of the \(M\) guard candidates such that the union of the sections covered by the selected guards equals \(\{1, 2, \ldots, N\}\). Each guard candidate can either be selected or not selected; the same candidate cannot be selected more than once.
高桥希望所有 \(N\) 个区段都被覆盖。具体而言,他希望从 \(M\) 名警卫候选人中选择一部分,使得被录用警卫所覆盖区段的并集等于 \(\{1, 2, \ldots, N\}\)。每名警卫候选人要么被录用要么不被录用;同一候选人不能被录用超过一次。

Find the minimum number of guards that need to be assigned. If it is impossible to cover all sections regardless of how the guards are selected, output \(-1\).
求需要录用的最少警卫人数。如果无论怎样选择警卫都无法覆盖所有区段,则输出 \(-1\)

【输入】

\(N\) \(M\)
\(L_1\) \(R_1\)
\(L_2\) \(R_2\)
\(\vdots\)
\(L_M\) \(R_M\)

  • The first line contains an integer \(N\) representing the number of sections and an integer \(M\) representing the number of guard candidates, separated by a space.
  • From the 2nd line to the \((M + 1)\)-th line, the range of sections each guard candidate can cover is given.
  • The \((i + 1)\)-th line (\(1 \leq i \leq M\)) contains the left endpoint \(L_i\) and right endpoint \(R_i\) of the range of sections that guard candidate \(i\) can cover, separated by a space.

【输出】

Output in a single line the minimum number of guards needed to cover all sections. If it is impossible, output \(-1\).

【输入样例】

10 3
1 5
3 7
6 10

【输出样例】

2

【解题思路】

image

【代码详解】

#include <bits/stdc++.h>
using namespace std;
const int N = 200005;
int n, m, cnt;  // n: 目标覆盖长度,m: 区间数量,cnt: 使用的区间数量
struct Node
{
    int l, r;  // 区间左右端点
}a[N];

// 比较函数:先按左端点升序,再按右端点升序
bool cmp(Node x, Node y)
{
    if (x.l != y.l)
    {
        return x.l < y.l;
    }
    return x.r < y.r;
}

int main()
{
    cin >> n >> m;  // 读入目标长度和区间数量
    for (int i = 1; i <= m; i++)
    {
        cin >> a[i].l >> a[i].r;  // 读入区间
    }

    sort(a + 1, a + m + 1, cmp);  // 将区间按左端点排序
    
    int r = 0;  // 当前已覆盖到的最右位置,初始为0
    
    for (int i = 1; i <= m && r < n; i++)  // 遍历区间,直到覆盖到n
    {
        // 如果当前区间的左端点大于r+1,说明有覆盖不到的位置
        if (a[i].l > r + 1)
        {
            cout << -1 << endl;
            return 0;
        }
        
        int maxr = 0, maxi = i;  // 记录可选的区间中最大的右端点和对应的下标
        
        // 找到所有左端点不超过r+1的区间中,右端点最大的那个
        for (int j = i; j <= m && a[j].l <= r + 1; j++)
        {
            if (a[j].r > maxr)
            {
                maxr = a[j].r;
                maxi = j;
            }
        }
        
        // 如果没有能扩展覆盖范围的区间
        if (maxr <= r)
        {
            cout << -1 << endl;
            return 0;    
        }
        
        r = maxr;  // 更新已覆盖的最右位置
        cnt++;  // 使用的区间数加1
        i = maxi;  // 跳转到最大右端点对应的区间
    }
    
    // 判断是否覆盖到目标长度n
    if (r >= n)
    {
        cout << cnt;
    }
    else
    {
        cout << -1 << endl;
    }
    return 0;
}

【运行结果】

10 3
1 5
3 7
6 10
2

E - Store Sales Management

【题目来源】

AtCoder:E - Store Sales Management

【题目描述】

Takahashi works at the headquarters of a retail company that operates a chain of stores nationwide. The company runs a system that centrally manages the sales of each store.
高桥在一家在全国范围内经营连锁店的零售公司总部工作。该公司运行着一个集中管理各门店销售额的系统。

There are \(N\) stores nationwide, each assigned a store number from \(1\) to \(N\). For each store \(i\) \((1 \leq i \leq N)\), an initial sales amount \(S_i\) is recorded.
全国共有 \(N\) 家门店,每家门店分配有一个从 \(1\)\(N\) 的门店编号。对于每家门店 \(i\)\(1 ≤ i ≤ N\)),记录有初始销售额 \(S_i\)

For business analysis, Takahashi needs to process a total of \(Q\) queries of the following \(2\) types, in the given order.
出于业务分析需要,高桥需要按给定顺序处理总共 \(Q\) 条以下两种类型的查询。

  • Type 1 (1 L R): Output the total sales amount of all stores whose store numbers are between \(L\) and \(R\) inclusive, that is, \(S_L + S_{L+1} + \cdots + S_R\).
    类型 1 (1 L R):输出门店编号在 \(L\)\(R\) 之间(包含两端)的所有门店的总销售额,即 \(S_L + S_{L+1} + ⋯ + S_R\)
  • Type 2 (2 X V): Overwrite the sales amount \(S_X\) of store \(X\) with \(V\). That is, set \(S_X \leftarrow V\).
    类型 2 (2 X V):将门店 \(X\) 的销售额 \(S_X\) 覆写为 \(V\)。即,设置 \(S_X ← V\)

For each Type 1 query, the total sales amount should be computed with all changes from previous Type 2 queries already applied.
对于每个类型 1 查询,计算总销售额时应已应用之前所有类型 2 查询的更改。

Please find the answer to each Type 1 query on behalf of Takahashi.
请代表高桥找出每个类型 1 查询的答案。

【输入】

\(N\) \(Q\)
\(S_1\) \(S_2\) \(\ldots\) \(S_N\)
\(\mathrm{query}_1\)
\(\mathrm{query}_2\)
\(\vdots\)
\(\mathrm{query}_Q\)

  • The first line contains the number of stores \(N\) and the number of queries \(Q\), separated by a space.
  • The second line contains the initial sales amounts \(S_1, S_2, \ldots, S_N\) of each store, separated by spaces.
  • The following \(Q\) lines each contain one of the \(Q\) queries. Each query is distinguished by the leading integer indicating its type. The \(i\)-th query \(\mathrm{query}_i\) is given in one of the following formats:
  • Type 1: 1 L R (compute the total sales amount of stores with numbers from \(L\) to \(R\) inclusive)
  • Type 2: 2 X V (overwrite the sales amount of store \(X\) with \(V\))

【输出】

Each time a Type 1 query is processed, output the corresponding total sales amount on a single line.

【输入样例】

5 4
10 20 30 40 50
1 1 3
2 2 100
1 1 3
1 2 5

【输出样例】

60
140
220

【解题思路】

image

【代码详解】

#include <bits/stdc++.h>
using namespace std;
#define int long long
const int N = 200005;
int n, q;  // n: 数组长度,q: 操作次数
int s[N], tr[N];  // s: 原数组,tr: 树状数组

// 获取x的最低位的1
int lowbit(int x)
{
    return x & -x;
}

// 树状数组更新:在位置x加上c
void add(int x, int c)
{
    for (int i = x; i <= n; i += lowbit(i))
    {
        tr[i] += c;
    }
}

// 树状数组查询:求前缀和[1, x]
int query(int x)
{
    int res = 0;
    for (int i = x; i; i -= lowbit(i))
    {
        res += tr[i];
    }
    return res;
}

signed main()
{
    cin >> n >> q;  // 读入数组长度和操作次数
    
    for (int i = 1; i <= n; i++)
    {
        cin >> s[i];  // 读入数组元素
        add(i, s[i]);  // 初始化树状数组
    }
    
    while (q--)  // 处理每个操作
    {
        int op; 
        cin >> op;  // 读入操作类型
        
        if (op == 1)  // 查询操作
        {
            int l, r;
            cin >> l >> r;  // 读入查询区间
            // 输出区间和:前缀和[r] - 前缀和[l-1]
            cout << query(r) - query(l - 1) << endl;
        }
        else  // 更新操作
        {
            int x, v;
            cin >> x >> v;  // 读入位置和新的值
            add(x, v - s[x]);  // 更新树状数组
            s[x] = v;  // 更新原数组
        }
    }
    return 0;
}

【运行结果】

5 4
10 20 30 40 50
1 1 3
60
2 2 100
1 1 3
140
1 2 5
220
posted @ 2026-03-01 14:06  团爸讲算法  阅读(0)  评论(0)    收藏  举报