线段树的题
纯瘤子题555
就是用最长子段和的思路,在每次赋值后记录端点就行
Code
#include<bits/stdc++.h>
using namespace std;
#define lson (rt<<1)
#define rson (rt<<1|1)
const int maxn=1e5+10;
int n,m;
struct node
{
int l,r;
long long sum,max_l,max_r,maxx;
long long l_right,r_left;
long long ll,rr;
}tree[maxn<<2];
int a[maxn];
void pushup(int rt)
{
tree[rt].sum = tree[lson].sum+tree[rson].sum;
if (tree[lson].max_l>=tree[lson].sum+tree[rson].max_l)
{
tree[rt].max_l = tree[lson].max_l;
tree[rt].l_right = tree[lson].l_right;
}
else
{
tree[rt].max_l = tree[lson].sum+tree[rson].max_l;
tree[rt].l_right = tree[rson].l_right;
}
if (tree[rson].max_r>tree[rson].sum+tree[lson].max_r)
{
tree[rt].max_r = tree[rson].max_r;
tree[rt].r_left = tree[rson].r_left;
}
else
{
tree[rt].max_r = tree[rson].sum+tree[lson].max_r;
tree[rt].r_left = tree[lson].r_left;
}
if (tree[lson].maxx>=max(tree[rson].maxx,tree[lson].max_r+tree[rson].max_l))
{
tree[rt].maxx = tree[lson].maxx;
tree[rt].ll = tree[lson].ll;
tree[rt].rr = tree[lson].rr;
}
else if (tree[rson].maxx>max(tree[lson].maxx,tree[lson].max_r+tree[rson].max_l))
{
tree[rt].maxx = tree[rson].maxx;
tree[rt].ll = tree[rson].ll;
tree[rt].rr = tree[rson].rr;
}
else
{
tree[rt].maxx = tree[lson].max_r+tree[rson].max_l;
tree[rt].ll = tree[lson].r_left;
tree[rt].rr = tree[rson].l_right;
}
}
void build(int rt,int l,int r)
{
tree[rt].l = l;
tree[rt].r = r;
if (l == r)
{
tree[rt].sum = a[l];
tree[rt].max_l = a[l];
tree[rt].max_r = a[l];
tree[rt].maxx = a[l];
tree[rt].ll=l;
tree[rt].rr=l;
tree[rt].l_right=l;
tree[rt].r_left=l;
return;
}
int mid = (l+r) >> 1;
build(lson,l,mid);
build(rson,mid+1,r);
pushup(rt);
}
node query(int rt,int l,int r)
{
if (tree[rt].l == l && tree[rt].r == r)
{
return tree[rt];
}
int mid = (tree[rt].l+tree[rt].r) >> 1;
if (r<=mid) return query(lson,l,r);
else if (l>mid) return query(rson,l,r);
else
{
node left = query(lson,l,mid);
node right = query(rson,mid+1,r);
node res;
res.sum = left.sum+right.sum;
if (left.max_l>=left.sum+right.max_l)
{
res.max_l = left.max_l;
res.l_right = left.l_right;
}
else
{
res.max_l = left.sum+right.max_l;
res.l_right = right.l_right;
}
if (right.max_r>right.sum+left.max_r)
{
res.max_r = right.max_r;
res.r_left = right.r_left;
}
else
{
res.max_r = right.sum+left.max_r;
res.r_left = left.r_left;
}
if (left.maxx>=max(right.maxx,left.max_r+right.max_l))
{
res.maxx = left.maxx;
res.ll = left.ll;
res.rr = left.rr;
}
else if (right.maxx>max(left.maxx,left.max_r+right.max_l))
{
res.maxx = right.maxx;
res.ll = right.ll;
res.rr = right.rr;
}
else
{
res.maxx = left.max_r+right.max_l;
res.ll = left.r_left;
res.rr = right.l_right;
}
return res;
}
}
int main()
{
cin >> n >> m;
for (int i=1;i<=n;i++) cin >> a[i];
build(1,1,n);
for (int i=1;i<=m;i++)
{
int x,y;
cin >> x >> y;
node ans=query(1,x,y);
cout << ans.ll << " " << ans.rr << " " << ans.maxx << endl;
}
return 0;
}