• hdu 3333 树状数组+离线处理


    思路:既然要求的是不同的元素的和,那么我们可以想办法让每个值在区间中只出现一次,于是想到了离线的算法:将查询按照右端点排序,位置在右端点之前的元素都插入到树状数组中,对于已经出现过的值,我们要先删除(在原位置)再插入(在cur的位置),因为很显然对于同一个元素,只有在最靠右的位置出现一次才能返回正确的查询结果。所以我们需要用map来记录每个值上一次插入的位置,删除后再插入到当前位置。

     1 #include <algorithm>
     2 #include <iostream>
     3 #include <cstring>
     4 #include <cstdio>
     5 #include <map>
     6 using namespace std;
     7 
     8 typedef long long ll;
     9 const int N = 30001;
    10 const int Q = 100001;
    11 ll c[N];
    12 ll ans[Q];
    13 int a[N];
    14 
    15 struct Query
    16 {
    17     int i, j, id;
    18     bool operator < ( const Query & o ) const 
    19     {
    20         return j < o.j;
    21     }
    22 } query[Q];
    23 
    24 map<int, int> mp;
    25 
    26 int lb( int i )
    27 {
    28     return i & -i;
    29 }
    30 
    31 void update( int i, int v )
    32 {
    33     while ( i < N )
    34     {
    35         c[i] += v;
    36         i += lb(i);        
    37     }
    38 }
    39 
    40 ll get( int i )
    41 {
    42     ll ans = 0;
    43     while ( i )
    44     {
    45         ans += c[i];
    46         i -= lb(i);
    47     }
    48     return ans;
    49 }
    50 
    51 int main ()
    52 {
    53     int t;
    54     scanf("%d", &t);
    55     while ( t-- )
    56     {
    57         int n, q;        
    58         scanf("%d", &n);
    59         for ( int i = 1; i <= n; i++ )
    60         {
    61             scanf("%d", a + i);            
    62         }
    63         scanf("%d", &q);
    64         for ( int i = 1; i <= q; i++ )
    65         {
    66             scanf("%d%d", &query[i].i, &query[i].j);        
    67             query[i].id = i;    
    68         }
    69         sort( query + 1, query + 1 + q );
    70         memset( c, 0, sizeof(c) );
    71         mp.clear();
    72         int cur = 1;
    73         for ( int i = 1; i <= q; i++ )
    74         {
    75             while ( cur <= query[i].j )
    76             {
    77                 if ( mp.count(a[cur]) )
    78                 {
    79                     int pos = mp[a[cur]];
    80                     update( pos, -a[cur] );
    81                 }
    82                 update( cur, a[cur] );
    83                 mp[a[cur]] = cur;
    84                 cur++;
    85             }
    86             ans[query[i].id] = get( query[i].j ) - get( query[i].i - 1 );
    87         }
    88         for ( int i = 1; i <= q; i++ )
    89         {
    90             printf("%I64d
    ", ans[i]);
    91         }
    92     }
    93     return 0;
    94 }
  • 相关阅读:
    ExtJs 第二章,Ext.form.Basic表单操作
    linux centos 下php的mcrypt扩展
    curl_errno错误码说明
    centos 安装composer
    虚拟机centOs Linux与Windows之间的文件传输
    CentOS 6.4 linux下编译安装 LNMP环境
    CentOS 6.4 php-fpm 添加service 添加平滑启动/重启
    CentOS 6.4 linux下编译安装MySQL5.6.14
    centOS linux 下PHP编译安装详解
    centOS linux 下nginx编译安装详解
  • 原文地址:https://www.cnblogs.com/huoxiayu/p/4687224.html
Copyright © 2020-2023  润新知