线段树算法一些题
POJ3264
/*
算法过程:
1.构建线段树
2.在线段树中插入数据
3.对线段树进行更新(该题无更新操作)和查询
*/
#include <cstdio>
#include <algorithm>
using namespace std;
const int INF = 0xffffff0;
struct node{
int l; //区间左端点
int r; //区间右端点
//下面是特殊设定的数据域
int minx, maxx; //区间中最高和最矮的奶牛身高
}tree[800010];
int minx = INF;
int maxx = -INF;
// 对区间l,r建立线段树
void build_tree(int i, int l, int r) {
//节点i的数据域的初始化(即根节点)
tree[i].l = l;
tree[i].r = r;
tree[i].minx = INF;
tree[i].maxx = -INF;
if(l != r) {
int mid = (l + r) / 2;
build_tree(2 * i + 1, l, mid);
build_tree(2 * i + 2, mid + 1, r);
}
}
void Insert(int root, int i, int h) {
if(tree[root].l == tree[root].r) {
tree[root].maxx = tree[root].minx = h;
return;
}
tree[root].minx = min(tree[root].minx, h);
tree[root].maxx = max(tree[root].maxx, h);
if(i <= (tree[root].l + tree[root].r) / 2) {
Insert(2 * root + 1, i, h);
} else {
Insert(2 * root + 2, i, h);
}
}
void query(int root, int a1, int a2) {
if(tree[root].minx >= minx && tree[root].maxx <= maxx) {
return;
}
if(tree[root].l == a1 && tree[root].r == a2) {
minx = min(minx, tree[root].minx);
maxx = max(maxx, tree[root].maxx);
return;
}
int mid = (tree[root].l + tree[root].r) / 2;
if(a2 <= mid) {
query(2 * root + 1, a1, a2);
} else if(a1 > mid) {
query(2 * root + 2, a1, a2);
} else {
query(2 * root + 1, a1, mid);
query(2 * root + 2, mid + 1, a2);
}
}
int main () {
int N, Q;
scanf("%d%d", &N, &Q);
build_tree(0, 1, N);
for(int i = 1; i <= N; ++i) {
int h;
scanf("%d", &h);
Insert(0, i, h);
}
while(Q--) {
int a1, a2;
scanf("%d%d", &a1, &a2);
minx = INF;
maxx = -INF;
query(0, a1, a2);
printf("%d\n", maxx - minx);
}
return 0;
}
HDU - 4027
#include<bits/stdc++.h>
const int MAXN = 100010;
typedef long long ll;
typedef struct node_s {
ll sum;
int l, r, len;
} node_t;
node_t tree[MAXN * 4];
void update_sum(int now) {
tree[now].sum = tree[now << 1].sum + tree[now << 1 | 1].sum;
}
void build_tree(int now, int l, int r) {
tree[now].l = l;
tree[now].r = r;
tree[now].len = tree[now].r - tree[now].l + 1;
if(tree[now].l == tree[now].r) {
scanf("%lld", &tree[now].sum);
return;
}
int mid = (tree[now].l + tree[now].r) >> 1;
build_tree(now << 1, l, mid);
build_tree(now << 1 | 1, mid + 1, r);
update_sum(now);
}
void update(int now, int l, int r) {
if(tree[now].sum == tree[now].len) return;
if(tree[now].l == tree[now].r) {
tree[now].sum = ll(sqrt(double(tree[now].sum)));
return;
}
int mid = (tree[now].l + tree[now].r) >> 1;
if(r <= mid) update(now << 1, l, r);
else if(l > mid) update(now << 1 | 1, l, r);
else {
update(now << 1, l, mid);
update(now << 1 | 1, mid + 1, r);
}
update_sum(now);
}
ll query(int now, int l, int r) {
if(tree[now].l == l && tree[now].r == r)
return tree[now].sum;
int mid = (tree[now].l + tree[now].r) >> 1;
if(r <= mid){
return query(now << 1, l, r);
} else if(l > mid) {
return query(now << 1 | 1, l, r);
} else {
return query(now << 1, l, mid) + query(now << 1 | 1, mid + 1, r);
}
}
int main () {
int size, q;
int case_num = 0;
while(~scanf("%d", &size)) {
printf("Case #%d:\n", ++case_num);
build_tree(1, 1, size);
scanf("%d", &q);
for(int i = 1; i <= q; ++i) {
int T, X, Y;
scanf("%d%d%d", &T, &X, &Y);
if(X > Y) {
X ^= Y, Y ^= X, X ^= Y;
}
if(T == 0) {
update(1, X, Y);
} else {
printf("%lld\n", query(1, X, Y));
}
}
printf("\n");
}
}
HDU - 1166
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
const int MAXN = 50010;
int val;
struct node{
int l;
int r;
int sum;
}tree[MAXN * 4];
void update_sum(int root) {
tree[root].sum = tree[root << 1].sum + tree[root << 1 | 1].sum;
}
void build_tree(int root, int l, int r) {
tree[root].l = l;
tree[root].r = r;
if(l == r) {
scanf("%d", &tree[root].sum);
return;
}
int mid = (l + r) >> 1;
build_tree(root << 1, l, mid);
build_tree(root << 1 | 1, mid + 1, r);
update_sum(root);
}
void ADD(int now, int l, int r) {
if(tree[now].l == tree[now].r) {
tree[now].sum += val;
return;
}
int mid = (tree[now].l + tree[now].r) >> 1;
if(r <= mid) {
ADD(now << 1, l, r);
} else if( l > mid) {
ADD(now << 1 | 1, l, r);
} else {
ADD(now << 1, l, mid);
ADD(now << 1 | 1, mid + 1, r);
}
update_sum(now);
}
ll QUERY(int now, int l, int r) {
if(tree[now].l == l && tree[now].r == r) {
return tree[now].sum;
}
int mid = (tree[now].l + tree[now].r) >> 1;
if(r <= mid) {
return QUERY(now << 1, l, r);
} else if(l > mid) {
return QUERY(now << 1 | 1, l, r);
} else {
return QUERY(now << 1, l, mid) + QUERY(now << 1 | 1, mid + 1, r);
}
}
int main () {
int T;
scanf("%d", &T);
int case_num = 0;
while(T--) {
printf("Case %d:\n", ++case_num);
int N;
scanf("%d", &N);
build_tree(1, 1, N);
string op;
int i;
while(cin >> op) {
if(op == "End") break;
scanf("%d%d", &i, &val);
if(op == "Add") {
ADD(1, i, i);
} else if(op == "Sub") {
val = -val;
ADD(1, i, i);
} else {
printf("%lld\n", QUERY(1, i, val));
}
}
}
return 0;
}
HDU 1754
#include<bits/stdc++.h>
using namespace std;
const int N = 200005;
const int INF = 0x3f3f3f3f;
struct node{
int l;
int r;
int maxx;
}tree[N * 4];
int maxx = -INF;
void update_maxx(int root) {
tree[root].maxx = max(tree[root << 1].maxx, tree[root << 1 | 1].maxx);
}
void build_tree(int root, int l, int r) {
tree[root].l = l;
tree[root].r = r;
if(l == r) {
scanf("%d", &tree[root].maxx);
return;
}
int mid = (l + r) >> 1;
build_tree(root << 1, l, mid);
build_tree(root << 1 | 1, mid + 1, r);
update_maxx(root);
}
void update(int root, int l, int r) {
if(tree[root].l == tree[root].r) {
tree[root].maxx = maxx;
return;
}
int mid = (tree[root].l + tree[root].r) >> 1;
if(r <= mid) {
update(root << 1, l, r);
} else if(l > mid) {
update(root << 1 | 1, l, r);
} else {
update(root << 1, l, mid);
update(root << 1 | 1, mid + 1, r);
}
update_maxx(root);
}
int query(int root, int l, int r) {
if(tree[root].l == l && tree[root].r == r) {
return tree[root].maxx;
}
int mid = (tree[root].l + tree[root].r) >> 1;
if(r <= mid) {
return query(root << 1, l, r);
} else if(l > mid) {
return query(root << 1 | 1, l, r);
} else {
return max(query(root << 1, l, mid), query(root << 1 | 1, mid + 1, r));
}
}
int main () {
int n, m;
while(~scanf("%d%d", &n, &m)) {
build_tree(1, 1, n);
while(m--) {
char op;
int x, y;
getchar();
scanf("%c%d%d", &op, &x, &y);
if(op == 'Q') {
if(x > y) {
x ^= y, y ^= x, x ^= y;
}
printf("%d\n", query(1, x, y));
} else {
maxx = y;
update(1, x, x);
}
}
}
return 0;
}
延迟标记 HDU1698
#include<bits/stdc++.h>
using namespace std;
const int MAXN = 100010;
struct node {
int l, r;
int sum, lazy;
} tree[MAXN << 2];
void update_maxx(int root) {
tree[root].sum = tree[root << 1].sum + tree[root << 1 | 1].sum;
}
void push_down(int root) {
if(tree[root].lazy) {
int l = root << 1;
int r = root << 1 | 1;
tree[l].lazy = tree[r].lazy = tree[root].lazy;
tree[l].sum = (tree[l].r - tree[l].l + 1) * tree[l].lazy;
tree[r].sum = (tree[r].r - tree[r].l + 1) * tree[r].lazy;
tree[root].lazy = 0;
}
}
void build_tree(int root, int l, int r) {
tree[root].l = l;
tree[root].r = r;
tree[root].lazy = 0;
if(l == r) {
tree[root].sum = 1;
return;
}
int mid = (l + r) >> 1;
build_tree(root << 1, l, mid);
build_tree(root << 1 | 1, mid + 1, r);
update_maxx(root);
}
void update(int root, int l, int r, int val) {
if(tree[root].l == l && tree[root].r == r) {
tree[root].lazy = val;
tree[root].sum = (r - l + 1) * val;
return;
}
push_down(root);
int mid = (tree[root].l + tree[root].r) >> 1;
if(r <= mid) {
update(root << 1, l, r, val);
} else if(l > mid) {
update(root << 1 | 1, l, r, val);
} else {
update(root << 1, l, mid, val);
update(root << 1 | 1, mid + 1, r, val);
}
update_maxx(root);
}
int query(int root, int l, int r) {
if(tree[root].l == l && tree[root].r == r) {
return tree[root].sum;
}
push_down(root);
int mid = (tree[root].l + tree[root].r) >> 1;
if(r <= mid) {
return query(root << 1, l, r);
} else if(l > mid) {
return query(root << 1 | 1, l, r);
} else{
return query(root << 1, l, mid) + query(root << 1 | 1, mid + 1, r);
}
}
int main () {
int T;
scanf("%d", &T);
int case_num = 0;
while(T--) {
int n;
scanf("%d", &n);
build_tree(1, 1, n);
int Q;
scanf("%d", &Q);
while(Q--) {
int x, y, val;
scanf("%d%d%d", &x, &y, &val);
update(1, x, y, val);
}
printf("Case %d: The total value of the hook is %d.\n", ++case_num, query(1, 1, n));
}
}
作者:LightAc
出处:https://www.cnblogs.com/lightac/
联系:
Email: dzz@stu.ouc.edu.cn
QQ: 1171613053
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文链接,否则保留追究法律责任的权利。