常熟哪里大了
查看原帖
常熟哪里大了
464004
ZepX_D楼主2024/7/3 15:42

感觉是两个 log 不至于跑不过去啊

#include <bits/stdc++.h>
#define pb push_back
#define LL long long

using namespace std;

const int N = 100010;
struct node{int l,r,x,y;}L[N<<5];

vector < int > ve[N];
int c[N],a[N],n,cnt;

void add(int k,int i)
{while(i <= n) c[i] += k,i += i&-i;}

int Q(int i)
{
	int res = 0;
	while(i) res += c[i],i -= i&-i;
	return res;
}

struct tree
{
	int l,r;
	set < int > v;
}tr[N<<2];

void build(int l,int r,int i)
{
	tr[i].l = l,tr[i].r = r;
	if(l == r) return ;
	int mid = (l+r)>>1;
	build(l,mid,i<<1),build(mid+1,r,i<<1|1);
}

void M(int l,int r,int id,int i)
{
	if(tr[i].l >= l && tr[i].r <= r)
		return (void)(tr[i].v.insert(id));
	if(tr[i<<1].r >= l) M(l,r,id,i<<1);
	if(tr[i<<1|1].l <= r) M(l,r,id,i<<1|1);
}

void del(int l,int r,int id,int i)
{
	if(tr[i].l >= l && tr[i].r <= r)
		return (void)(tr[i].v.erase(lower_bound(begin(tr[i].v),end(tr[i].v),id)));
	if(tr[i<<1].r >= l) del(l,r,id,i<<1);
	if(tr[i<<1|1].l <= r) del(l,r,id,i<<1|1);
}

vector < int > tmp;

void Q1(int p,int i)
{
	for (int k : tr[i].v) tmp.pb(k);
	if(tr[i].l == tr[i].r) return ;
	if(p <= tr[i<<1].r) Q1(p,i<<1);
	else Q1(p,i<<1|1);
}

int main()
{
	int m;cin >> n >> m;
	for (int i = 1;i <= n;i++)
	{
		for (int j = i;;j += i)
		{
			L[++cnt] = {j-i+1,min(j,n),i,j/i},ve[i].pb(j/i);
			if(j >= n) break;
		}
		ve[i].pb((n-1)/i+2);
	}
	build(1,n,1);
	for (int i = 1;i <= cnt;i++) M(L[i].l,L[i].r,i,1);
	for (int i = 1;i <= n;i++) add(1,i),a[i] = 1;
	while(m--)
	{
		int op,l,r;cin >> op >> l;
		if(op == 1)
		{
			tmp.clear();Q1(l,1);
			for (int i : tmp)
			{
				ve[L[i].x].erase(lower_bound(begin(ve[L[i].x]),end(ve[L[i].x]),L[i].y));
				int k = ve[L[i].x][0];
				add(k-a[L[i].x],L[i].x),a[L[i].x] = k;
				del(L[i].l,L[i].r,i,1);
			}
		}
		else cin >> r,cout << Q(r)-Q(l-1) << '\n';
	}
	return 0;
}
2024/7/3 15:42
加载中...