`

【线段树】北大 poj 3468 A Simple Problem with Integers

阅读更多

 

/* THE PROGRAM IS MADE BY PYY */
/*----------------------------------------------------------------------------//
    Copyright (c) 2012 panyanyany All rights reserved.

    URL   : http://poj.org/problem?id=3468
    Name  : 3468 A Simple Problem with Integers

    Date  : Sunday, April 15, 2012
    Time Stage : 2 hours

    Result:
10074419	panyanyany
3468
Accepted	12492K	2047MS	C++
3148B	2012-04-15 12:46:56

Test Data :

Review :
普通的线段树方法要超时的,貌似还可以用splay tree(伸展树)。小媛的博客上说要用lazy方法……
//----------------------------------------------------------------------------*/

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <math.h>
#include <vector>

#include <algorithm>
#include <iostream>
#include <queue>

using namespace std ;

#define MEM(a, v)        memset (a, v, sizeof (a))    // a for address, v for value
#define max(x, y)        ((x) > (y) ? (x) : (y))
#define min(x, y)        ((x) < (y) ? (x) : (y))

#define INF     (0x3f3f3f3f)
#define MAXN 100010
#define LESN 10002

#define L(x)	((x)<<1)
#define R(x)	(((x)<<1)|1)

#define DB    /##/
typedef __int64	LL;

struct NODE {
	int lf, rh;
	LL sm, inc;
};

int		q, n;
NODE	segTree[MAXN*6]; 	//开小了一直runtime error
LL		inc;

void build(int id, int lf, int rh)
{
	segTree[id].lf = lf;
	segTree[id].rh = rh;
	segTree[id].sm = 0;
	segTree[id].inc = 0;

	if (lf == rh)
		return ;

	int mid = (lf + rh) / 2;
	build(id<<1, lf, mid);
	build((id<<1)|1, mid+1, rh);
}

LL update(int id, int lf, int rh, int val)
{
	// 不在当前区间(一般来说都不用判断这个……)
	if (segTree[id].lf > rh || segTree[id].rh < lf)
		return 0;

	// 到达匹配区间,这里不深入更新每一个叶子,因为会超时
	if (segTree[id].lf == lf && segTree[id].rh == rh)
	{
		segTree[id].inc += val;
		segTree[id].sm += val*(rh-lf+1);
		return val*(rh-lf+1);
	}

	int mid = (segTree[id].lf + segTree[id].rh) / 2;
	LL sum;

	if (rh <= mid)
		sum = update(id<<1, lf, rh, val);
	else if (mid < lf)
		sum = update((id<<1)|1, lf, rh, val);
	else
		sum = update(id<<1, lf, mid, val) + update((id<<1)|1, mid+1, rh, val);

	segTree[id].sm += sum;
	return sum;
}

LL query(int id, int lf, int rh)
{
	if (rh < segTree[id].lf || segTree[id].rh < lf)
	{
		return 0;
	}

	if (inc = segTree[id].inc)
	{	//查询的时候才更新子节点的增量
		segTree[L(id)].inc += inc; 	//相当于对子区间进行一次update
		segTree[L(id)].sm += inc * (segTree[L(id)].rh - segTree[L(id)].lf + 1);
		segTree[R(id)].inc += inc;
		segTree[R(id)].sm += inc * (segTree[R(id)].rh - segTree[R(id)].lf + 1);
		segTree[id].inc = 0; 	//增量都传递到子区间去了,这里就要置零
	}


	if (lf == segTree[id].lf && rh == segTree[id].rh)
		return segTree[id].sm;

	int mid = (segTree[id].lf + segTree[id].rh) / 2;

	if (rh <= mid)
		return query(id<<1, lf, rh);
	else if (mid < lf)
		return query((id<<1)|1, lf, rh);
	
	return query(id<<1, lf, mid) + query((id<<1)|1, mid+1, rh);
}

int main()
{
	int i, j, x, y, v;
	LL res;
	char c;
	while (scanf("%d%d", &n, &q) != EOF)
	{
		build(1, 1, n);
		for (i = 1; i <= n; ++i)
		{
			scanf("%d", &j);
			update(1, i, i, j);
		}
		while (q--)
		{
			getchar();
			scanf("%c", &c);
			scanf("%d %d", &x, &y);
			if ('Q' == c)
			{
				res = query(1, x, y);
				printf ("%I64d\n", res);
			}
			else
			{
				scanf("%d", &v);
				update(1, x, y, v);
			}
		}
	}
	return 0;
}
 
0
0
分享到:
评论

相关推荐

    线段树入门学习(二)(兼解POJ3468) JAVA

    在本教程中,我们将深入探讨线段树的基本概念,以及如何使用Java实现线段树来解决实际问题,如POJ3468题目。 首先,理解线段树的核心在于它的分治思想。线段树将一个大区间(通常是一维数组)分成多个小区间,每个...

    线段树练习POJ 3264

    线段树是一种数据结构,常用于处理区间查询与更新的问题,它能高效地支持动态维护区间最值、求和等问题。在本题“POJ 3264”中,我们可能面临的是一个区间最值或者区间求和的计算任务。线段树的基本思想是将数组或...

    POJ3468.zip_poj3468

    标题中的"POJ3468.zip_poj3468"显然与编程竞赛相关,POJ(Problemset Online Judge)是北京大学主办的一个在线编程竞赛平台,其中的3468是一个具体的题目编号。这个题目可能涉及到编程挑战,要求参赛者解决特定的...

    POJ3468.zip_ACM

    标题中的"POJ3468.zip_ACM"暗示了这是一个与ACM(国际大学生程序设计竞赛)相关的项目。在ACM比赛中,参赛者需要解决各种算法问题,以提高编程和解决问题的能力。"POJ3468"是这个特定问题的编号,在编程竞赛平台上的...

    POJ3277.rar_3277 poj_poj3277_多个面积_线段树

    标题中的“POJ3277.rar_3277 poj_poj3277_多个面积_线段树”是指一个与编程竞赛相关的压缩文件,特别提到了POJ(Problemset Online Judge)的第3277号问题。POJ是一个著名的在线编程竞赛平台,参与者需要解决各种...

    线段树入门学习(三)懒操作(兼解POJ1823) JAVA

    在本篇博文中,我们将深入探讨线段树的概念,以及如何实现懒惰更新(Lazy Propagation)策略,同时结合POJ1823问题进行实战应用。懒惰更新是优化线段树性能的关键技巧,它避免了频繁地对每个节点进行更新,从而减少...

    POJ1321-Chess Problem

    【标题】"POJ1321-Chess Problem" 是一个来自北京大学在线判题系统POJ(Problem Set)的编程题目。这个题目涉及到的主要知识点是算法设计与实现,特别是图论中的二分图匹配问题。 【描述】描述简单,表明这是一道与...

    poj 2352 stars(树状数组,线段树)

    ### POJ 2352 Stars - 树状数组与线段树实现 #### 题目背景 POJ 2352 Stars 是一道经典的算法题目,它提供了使用树状数组或线段树来解决的可能性。这两种数据结构都是为了高效处理区间查询问题而设计的。在这篇...

    poj2823.cpp.tar.gz_线段树

    在`poj2823.cpp`源代码中,我们可以看到实现线段树的具体细节,包括如何初始化、更新以及查询线段树。此外,代码可能还包括了问题的输入输出处理,错误检查,以及可能的优化策略,比如lazy propagation(惰性传播)...

    北大POJ部分题目答案(一些基础题目)

    很多的POJ题目答案!1000~1008,1011~1014,1016,1017,1019,1028,1032,1045,1046,1047,1050,1061,1067,1068,1088,1102,1159,1163,1183,1207,1218,1226,1247,1256,1258,1298,1316,1323,...

    POJ2528-Mayor's posters【区间映射压缩(离散化)+线段树】

    POJ2528-Mayor's posters 【区间映射压缩(离散化)+线段树】 解题报告+AC代码 http://hi.csdn.net/!s/83XZJU ========&gt; 我的所有POJ解题报告链接: http://blog.csdn.net/lyy289065406/article/details/6642573

    北大POJ 大量解题代码

    【标题】"北大POJ大量解题代码"指的是北京大学在线编程平台POJ上的一系列算法题目解决方案的集合。这些代码通常由ACM(国际大学生程序设计竞赛)参赛者或爱好者编写,旨在帮助学习者理解并解决各类算法问题,提高...

    北大POJ经典结题报告

    《北大POJ经典结题报告》是一份针对北京大学在线编程平台POJ的解题报告,旨在帮助学习者掌握算法和编程技巧,提升解决问题的能力。POJ(Problem Online Judge)是北大的一个在线编程竞赛系统,提供了丰富的算法题目...

    线段树例题(唐文斌).pdf

    ### 线段树例题解析 #### Brackets (SPOJ61, BRCKTS) **题目描述:** 此题要求我们维护一个长度为 \(N\) 的小括号序列 \(A\),并支持两种操作: 1. **Replace(i)**:将第 \(i\) 个位置的括号方向反转。 2. **Check...

    北京大学poj题目类型分类

    北京大学POJ题目类型分类 北京大学POJ题目类型分类是根据题目的难易程度、知识领域和解决方法对POJ题目进行分类的。通过对POJ题目的分类,可以帮助学习者更好地理解和掌握算法和数据结构的知识。 简单题 简单题是...

    北大acm题解(poj题目分析)

    《北大ACM题解》是一本专为解决POJ(Programming Online Judge)平台上的编程竞赛题目而编写的指导书籍。ACM(国际大学生程序设计竞赛,International Collegiate Programming Contest)是一项全球性的比赛,旨在...

    北大poj解题报告

    北京大学在线编程平台POJ(PKU Online Judge)是许多学习算法和进行编程训练的学生们的重要实践场所。这个“北大poj解题报告”包含了作者在使用POJ平台解题过程中的学习总结和经验分享,旨在帮助软件工程专业的学生...

    POJ 部分题解 解题报告

    6. **POJ 3468 线段树--long long VS int.txt**:线段树是处理区间查询和更新的有效数据结构。这个题目可能关注的是在处理大整数时,线段树的实现细节,尤其是`long long`类型与`int`类型的区别以及其在处理溢出问题...

    北大POJ初级-简单搜索

    【北大POJ初级-简单搜索】是北京大学在线判题系统POJ(Problem Online Judge)针对初学者设置的一类编程题目,主要涉及基础的算法和数据结构应用。这类问题通常不会过于复杂,旨在帮助学习者掌握基本的编程思维和...

    POJ2996-Help Me with the Game

    【标题】"POJ2996-Help Me with the Game"是一道源自北京大学在线判题系统POJ的编程竞赛题目。这道题目的主要目标是编写程序来解决一个特定的游戏策略问题,要求参赛者具备扎实的算法基础和编程能力。 【描述】...

Global site tag (gtag.js) - Google Analytics