zoukankan      html  css  js  c++  java
  • [CF]301D Yaroslav and Divisors

    CF 301D Yaroslav and Divisors 

    题意:给出n的一个排列,每次询问一个区间内有多少对数满足一个数是另一个数的因数。(n<=2e5)

    将询问离线排序后从左往右扫,每次对于当前位置的数找它所有倍数出现的位置p,如果p<= i,则在i位置上加一,否则在p位置上记录i,当再次扫到p时在i位置上加一。每次扫描到区间右端点时用树状数组统计答案。

    #include<bits/stdc++.h>
    #define N 200020
     
    using namespace std;
     
    int a[N], b[N], c[N], r[N], l[N], ans[N], n, m;
    vector<int> ask[N];
    vector<int> d[N];
     
    void add(int x)
    {
        while(x<= n)
        {
            c[x]++;
            x+= x&-x;
        }
    }
     
    int sum(int x)
    {
        int s= 0;
        while(x)
        {
            s+= c[x];
            x-= x&-x;
        }
        return s;
    }
     
    int main()
    {
        while(scanf("%d%d", &n, &m)== 2)
        {
            for(int i= 1; i<= n; i++)
            {
                scanf("%d", &a[i]);
                b[a[i]]= i;
            }
            for(int i= 1; i<= m; i++)
            {
                scanf("%d%d", &l[i], &r[i]);
                ask[r[i]].push_back(i);
            }
            for(int i= 1; i<= n; i++)
            {
                for(int j= 0; j< (int)d[i].size(); j++) add(d[i][j]);
                for(int j= 1; j* a[i]<= n; j++)
                {
                    int p= b[j* a[i]];
                    if(p<= i) add(p);
                    else d[p].push_back(i);
                }
                for(int j= 0; j< (int)ask[i].size(); j++)
                {
                    int p= ask[i][j];
                    ans[p]= sum(r[p])- sum(l[p]- 1);
                }
            }
            for(int i= 1; i<= m; i++) printf("%d
    ", ans[i]);
        }
        return 0;
    }
  • 相关阅读:
    SDL_mixer 播放wav
    SDL_mixer 播放mp3
    [转]音频基础知识及编码原理
    [转]QT父子与QT对象delete
    [转]QT中嵌入SDL
    [转]PCM文件格式
    [转]ffmpeg库音频解码示例
    C# 向PivotItem中添加子控件
    初识 Windows Phone 7
    C#语言使用Windows phone 中的数据数据绑定
  • 原文地址:https://www.cnblogs.com/xutianshu/p/10616825.html
Copyright © 2011-2022 走看看