+ query segment tree sorting section E - No Pain No Game segment tree ordering off-line processing interval

https://nanti.jisuanke.com/t/41391

The subject is not hard to figure, more violence, but to be computational complexity, computational complexity does not, will feel that their algorithm time out, not actually.

This topic is all about direct violence to obtain a multiple of the number and every number in less than 1e5, and then update, as previously written E - No Pain No Game segment tree offline processing section ordering  the same

Count complexity, harmonic series use twice, once to ask about the number of time to seek multiple, complexity is n * logn so on average about a number of each is about the logn 

Because there is a double relationship so that 2 * logn

The complexity of the tree line, and each update is logn, to traverse time

Therefore, the overall complexity is 2 * n * logn * logn, this certainly will not time out.

#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <queue>
#include <algorithm>
#include <iostream>
#define inf 0x3f3f3f3f
using namespace std;
const int maxn = 1e5 + 10;
typedef long long ll;
vector<int>num[maxn];
int a[maxn], vis[maxn], c[maxn], ans[maxn];
int n, m;
struct node
{
    int l, r, id;
    node(int l=0,int r=0,int id=0):l(l),r(r),id(id){}
}ex[maxn];
bool cmp(node a,node b)
{
    return a.r < b.r;
}

int lowbit(int x)
{
    return x & (-x);
}

void update(int x,int k)
{
    while (x <= n) {
        c[x] += k;
        x += lowbit(x);
    }
}

intGetSum ( int X) 
{ 
    int ANS = 0 ;
     the while (X> 0 ) { 
        ANS + = C [X]; 
        X - = lowbit (X); 
    } 
    return ANS; 
} 

int main () 
{ 
    for ( int I = . 1 ; I <MAXN; ++ I) {
         for ( int J = 2 * I; J <MAXN; = J + I) { 
            NUM [J] .push_back (I); // put factor for each of which the number of playing table, the harmonic series apparent complexity O (nlog n-) 
        } 
    }
    for (int i = 1; i < maxn; ++i) {
        for (int j = 2 * i; j < maxn; j += i) {
            num[i].push_back(j);
        }
    }
    scanf("%d%d", &n, &m);
    for (int i = 1; i <= n; i++) scanf("%d", &a[i]);
    for (int i = 1; i <= m; i++) {
        int l, r;
        scanf("%d%d", &l, &r);
        ex[i] = node(l, r, i);
    }
    memset(vis, -1, sizeof(vis));
    sort(ex + 1, ex + 1 + m, cmp);
    int now = 1;
    for (int i = 1; i <= n; i++) {
        int x = a[i];
        for (int j = 0; j < num[x].size(); j++) {
            int y = num[x][j];
            if (vis[y] != -1) update(vis[y], 1);
        }
        vis[x] = i;
        while (now <= m && i == ex[now].r) {
            int res = getsum(ex[now].r) - getsum(ex[now].l - 1);
            ans[ex[now].id] = res;
            now++;
        }
    }
    for (int i = 1; i <= m; i++) printf("%d\n", ans[i]);
    return 0;
}
View Code

 

Guess you like

Origin www.cnblogs.com/EchoZQN/p/11521242.html