感觉是两个 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;
}