萌新求助ODT树
  • 板块P5350 序列
  • 楼主qfpjm
  • 当前回复2
  • 已保存回复2
  • 发布时间2022/7/28 16:31
  • 上次更新2023/10/27 17:59:57
查看原帖
萌新求助ODT树
342868
qfpjm楼主2022/7/28 16:31
#include <bits/stdc++.h>

using namespace std;

struct node
{
	int l, r;
	mutable long long v;
	node(int L, int R = 0, long long V = 0) : l(L), r(R), v(V) {}
	bool operator < (const node& o) const
	{
		return l < o.l;
	}
};

const long long mod = 1e9 + 7;
int n, m;
long long a[100005];
set<node> s;
vector<node> tmp, tmp2;

set<node>::iterator split(int pos)
{
    set<node>::iterator it = s.lower_bound(node(pos));
    if (it != s.end() && it -> l == pos)
    {
        return it;
    }
    it --;
    if (it -> r < pos)
    {
        return s.end();
    }
    int l = it -> l;
    int r = it -> r;
    long long v = it -> v;
    s.erase(it);
    s.insert(node(l, pos - 1, v));
    return s.insert(node(pos, r, v)).first;
}

void add(int l, int r, long long val)
{
	set<node>::iterator it2 = split(r + 1), it1 = split(l);
	for ( ; it1 != it2 ; it1 ++)
	{
		it1 -> v += val;
	}
}

void assign(int l, int r, long long val)
{
	set<node>::iterator it2 = split(r + 1), it1 = split(l);
	s.erase(it1, it2);
	s.insert(node(l, r, val));
}

long long sum(int l, int r)
{
	set<node>::iterator it2 = split(r + 1), it1 = split(l);
	long long ans = 0;
	for ( ; it1 != it2 ; it1 ++)
	{
		ans = (ans % mod + (it1 -> r - it1 -> l + 1) * it1 -> v % mod) % mod;
	}
	return ans;
}

void cpy(int l, int r, int l2, int r2)
{
	set<node>::iterator it2 = split(r + 1), it1 = split(l);
	for ( ; it1 != it2 ; it1 ++)
	{
		tmp.push_back(node(it1 -> l, it1 -> r, it1 -> v));
	}
	set<node>::iterator it4 = split(r2 + 1), it3 = split(l2);
	s.erase(it3, it4);
	for (int i = 0 ; i < tmp.size() ; i ++)
	{
		s.insert(node(tmp[i].l - l + l2, tmp[i].r - r + r2, tmp[i].v));
	}
	tmp.clear();
}

void exc(int l, int r, int l2, int r2)
{
	set<node>::iterator it2 = split(r + 1), it1 = split(l);
	for (set<node>::iterator it = it1 ; it != it2 ; it ++)
	{
		tmp.push_back(node(it -> l, it -> r, it -> v));
	}
	set<node>::iterator it4 = split(r2 + 1), it3 = split(l2 + 1);
	for (set<node>::iterator it = it3 ; it != it4 ; it ++)
	{
		tmp2.push_back(node(it -> l, it -> r, it -> v));
	}
	s.erase(it1, it2);
	s.erase(it3, it4);
	for (int i = 0 ; i < tmp.size() ; i ++)
	{
		s.insert(node(tmp[i].l + l - l2, tmp[i].r + l - l2, tmp[i].v));
	}
	for (int i = 0 ; i < tmp2.size() ; i ++)
	{
		s.insert(node(tmp2[i].l + l2 - l, tmp2[i].r + r2 - r, tmp2[i].v));
	}
	tmp.clear();
	tmp2.clear();
}

void rev(int l, int r)
{
	set<node>::iterator it2 = split(r + 1), it1 = split(l);
	for (set<node>::iterator it = it1 ; it != it2 ; it ++)
	{
		tmp.push_back(node(it -> l, it -> r, it -> v));
	}
	s.erase(it1, it2);
	for (int i = 0 ; i < tmp.size() ; i ++)
	{
		s.insert(node(l + r - tmp[i].r, l + r - tmp[i].l, tmp[i].v));
	}
	tmp.clear();
}

int main()
{
	cin >> n >> m;
	for (int i = 1 ; i <= n ; i ++)
	{
		cin >> a[i];
		s.insert(node(i, i, a[i]));
	}
	while (m --)
	{
		int opt, l, r;
		cin >> opt >> l >> r;
		if (opt == 1)
		{
			cout << sum(l, r) << endl;
		}
		else if (opt == 2)
		{
			long long x;
			cin >> x;
			assign(l, r, x);
		}
		else if (opt == 3)
		{
			long long x;
			cin >> x;
			add(l, r, x);
		}
		else if (opt == 4)
		{
			int l2, r2;
			cin >> l2 >> r2;
			cpy(l, r, l2, r2);
		}
		else if (opt == 5)
		{
			int l2, r2;
			cin >> l2 >> r2;
			exc(l, r, l2, r2);
		}
		else if (opt == 6)
		{
			rev(l, r);
		}
	}
	set<node>::iterator it2 = split(n + 1), it1 = split(1);
	for ( ; it1 != it2 ; it1 ++)
	{
		for (int i = 1 ; i <= it1 -> r - it1 -> l + 1 ; i ++)
		{
			cout << it1 -> v << " ";
		}
	}
}
2022/7/28 16:31
加载中...