【HDU】4027 Can you answer these queries? (线段树)

本文深入解析了区间数开方并向下取整的问题,详细讲解了算法实现过程,包括处理边界条件、使用线段树优化查询效率等关键步骤。通过实例演示,帮助读者理解并掌握该算法的应用。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

题目大意:对区间的数开方,并向下取整。

题目有一个坑点,会出现左边大于右边,然后需要交换左右,而不是不处理。坑!

#define _CRT_SECURE_NO_WARNINGS
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<algorithm>
using namespace std;
#define MAX 100005
#define ls rt<<1
#define rs ls|1
#define m (l+r)>>1
long long sum[MAX << 2];
bool tg[MAX << 2];

void uprt(int rt)
{
	tg[rt] = (tg[rs] || tg[ls]);
	sum[rt] = sum[ls] + sum[rs];
}

void updata(int L, int R, int l, int r, int rt)
{
	if (L <= l&&r <= R)
	{
		if (!tg[rt])
		{
			return;
		}
	}
	if (l == r)
	{
		sum[rt] = floor(sqrt(sum[rt]));
		if (sum[rt]<=1)
			tg[rt] = false;
		return;
	}
	int mid = m;
	if (L <= mid)
		updata(L, R, l, mid, ls);
	if (mid < R)
		updata(L, R, mid + 1, r, rs);
	uprt(rt);
}

long long query(int L, int R, int l, int r, int rt)
{
	if (L <= l&&r <= R)
	{
		return sum[rt];
	}
	int mid = m;
	long long ans = 0;
	if (L <= mid)
		ans = query(L, R, l, mid, ls);
	if (mid < R)
		ans += query(L, R, mid + 1, r, rs);
	return ans;
}

void build(int l, int r, int rt)
{
	if (l == r)
	{
		scanf("%lld", &sum[rt]);
		tg[rt] = 1;
		if (sum[rt] <= 1)
			tg[rt] = 0;
		return;
	}
	int mid = m;
	build(l, mid, ls);
	build(mid + 1, r, rs);
	uprt(rt);
}

int main()
{
	int icase = 1;
	int n;
	while (~scanf("%d", &n))
	{
			
		build(1, n, 1);
		int k, a, b, c;
		cin >> k;
		printf("Case #%d:\n",icase++);
		while (k--)
		{
			scanf("%d%d%d", &a, &b, &c);
			if (b > c)
			{
				b = b + c;
				c = b - c;
				b = b - c;
			}
			if (a == 0)
			{
				updata(b, c, 1, n, 1);
			}
			else
			{
				printf("%lld\n", query(b, c, 1, n, 1));
			}
		}
		puts("");
	}
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值