第三届全国大学生算法设计与编程挑战赛题解【金奖全国第九】

这次秋季赛查重后有效提交队伍共1000余队,前5%金,10%银,20%铜,冠军1名,亚军2名,季军3名。每次比赛之余都不得不感慨oier的可怕实力和某些竞赛强省的高端水平。

赛时一直稳定在前5%(金奖行列),一度干到第七,傻瓜式地读错题加了罚时,最后开了A题,600多行代码超时了,短时间内想不到好的解决方案,最终gg辽~ 没能拿到季军的奖牌.

总体感觉不错,C题(几何题)提交AC后,队友说数据有点水,不然可能过不了,但由于在比赛冲奖,就没有多看。其他题还好,几乎没有什么太大的失误。A题可惜没能做出来,因为没有做对就没贴上来,后来账号登不上,连代码都看不到了... 就有点迷

比赛一开始先切了F题、然后队友跟榜看J题,说题意有点迷,就帮他一起读了一下,避免了罚时。接着切了B题,没睡醒RE了一次,队友这时在看D题,我去做了C,AC后冲到15名,这时候其实保不了金的,毕竟比赛才进行一个小时左右,只能继续做...

具体的过程在下面了,前面就不再啰嗦了hh


目录

☀️| B-二进制

⭐️题面

⭐️题解

⭐️代码

☀️| C-不正方形

⭐️题面

⭐️题解

⭐️代码

☀️| D-分配颜色

⭐️题面

⭐️题解

⭐️代码

☀️| E-土地规划

⭐️题面

⭐️题解

⭐️代码

☀️| F-CTF

⭐️题面

⭐️题解

⭐️代码

☀️| G-希望

⭐️题面

⭐️题解

⭐️代码

☀️| I-排队队

⭐️题面

⭐️题解

⭐️代码

☀️| J-抽奖

⭐️题面

⭐️题解

⭐️代码


☀️| B-二进制

⭐️题面

⭐️题解

build tree,根据op的值判断要 modify 还是 query,做出具体的操作模拟实现

⭐️代码

#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N = 1e5 + 10;
int n, q, a[N];

struct Node{
    int l, r;
    ll sum, lazy;
}tree[11][N << 2];

void pushup(int id, int pos)
{
    tree[id][pos].sum = tree[id][pos << 1].sum + tree[id][pos << 1 | 1].sum;
}

void pushdown(int id, int pos)
{
    auto &root = tree[id][pos], &left = tree[id][pos << 1], &right = tree[id][pos << 1 | 1];
    if (root.lazy)
    {
        left.sum += 1LL * (left.r - left.l + 1) * root.lazy;
        right.sum += 1LL * (right.r - right.l + 1) * root.lazy;
        left.lazy += root.lazy, right.lazy += root.lazy;
        root.lazy = 0;
    }
}
void build(int id, int pos, int l, int r)
{
    tree[id][pos] = {l, r, 0, 0};
    if (l == r)
    {
        tree[id][pos] = {l, l, a[l], 0};
        return;
    }
    int mid = l + r >> 1;
    build(id, pos << 1, l, mid);
    build(id, pos << 1 | 1, mid + 1, r);
    pushup(id, pos);
}

void modify(int id, int pos, int l, int r, int val)
{
    if (l <= tree[id][pos].l && tree[id][pos].r <= r)
    {
        tree[id][pos].sum += 1LL * (tree[id][pos].r - tree[id][pos].l + 1) * val;
        tree[id][pos].lazy += val;
        return;
    }
    pushdown(id, pos);
    int mid = tree[id][pos].l + tree[id][pos].r >> 1;
    if (l <= mid) modify(id, pos << 1, l, r, val);
    if (mid < r) modify(id, pos << 1 | 1, l, r, val);
    pushup(id, pos);
}

ll query(int id, int pos, int l, int r)
{
    if (l <= tree[id][pos].l && tree[id][pos].r <= r) return tree[id][pos].sum;
    pushdown(id, pos);
    int mid = tree[id][pos].l + tree[id][pos].r >> 1;
    ll sum = 0;
    if (l <= mid) sum += query(id, pos << 1, l, r);
    if (mid < r) sum += query(id, pos << 1 | 1, l, r);
    return sum;
}

int main()
{
    scanf("%d %d", &n, &q);
    for (int i = 0; i <= 10; i++)
    	build(i, 1, 1, n);
    while (q--)
    {
    	int op; scanf("%d", &op);
    	if (op == 1) {
			int l, r;
    		int st, val; scanf("%d %d", &st, &l);
    		scanf("%d %d", &r, &val);
    		for (int i = 0; i <= 10; i++) {
    			if ((st >> i) & 1) {
    				modify(i, 1, l, r, val);
				}
			}
		}
		else {
			int st; 
			scanf("%d", &st);
    		int l, r; 
			scanf("%d %d", &l, &r);
    		ll ans = 0;
    		for (int i = 0; i <= 10; i++) {
    			if ((st >> i) & 1) ans += query(i, 1, l, r);
			}
			printf("%lld\n", ans);
		}
	}
    return 0;
}

☀️| C-不正方形

评论 5
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

米莱虾

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值