• HDU4027 Can you answer these queries?


      原题传送:http://acm.hdu.edu.cn/showproblem.php?pid=4027

      线段树。

      一个很大的数(< 263),最多也就进行几次开平方操作就会达到1了,所以每次更新,如果区间有的点不为1,那么就直接更新它,如果,区间的值都是1了,那么必须直接返回。

    View Code
     1 #include <stdio.h>
     2 #include <string.h>
     3 #include <math.h>
     4 #include <stdlib.h>
     5 #define lson (cur << 1)
     6 #define rson (cur << 1 | 1)
     7 #define N 100005
     8 #define LL __int64
     9 
    10 int n, m;
    11 LL a[N];
    12 LL tree[N << 2];  // 记录区间最大值,如果最大值为1,说明该区间值全为1
    13 LL sum[N << 2];
    14 
    15 inline LL max(LL x, LL y){return x > y ? x : y;}
    16 inline void swap(int &x, int &y){int tmp = x; x = y; y = tmp;}
    17 
    18 void pushup(int cur)
    19 {
    20     tree[cur] = max(tree[lson], tree[rson]);
    21     sum[cur] = sum[lson] + sum[rson];
    22 }
    23 
    24 void update(int cur, int l, int r, int s, int t)
    25 {
    26     if(tree[cur] == 1)
    27         return ;
    28     if(l == r)
    29     {
    30         tree[cur] = (LL)sqrt((double)tree[cur]);
    31         sum[cur] = tree[cur];
    32         return ;
    33     }
    34     int mid = (l + r) >> 1;
    35     if(mid >= s)
    36         update(lson, l, mid, s, t);
    37     if(mid < t)
    38         update(rson, mid + 1, r, s, t);
    39     pushup(cur);
    40 }
    41 
    42 void query(int cur, int l, int r, int s, int t, LL &ans)
    43 {
    44     if(l >= s && r <= t)
    45     {
    46         ans += sum[cur];
    47         return ;
    48     }
    49     int mid = (l + r) >> 1;
    50     if(mid >= s)
    51         query(lson, l, mid, s, t, ans);
    52     if(mid + 1 <= t)
    53         query(rson, mid + 1, r, s, t, ans);
    54 }
    55 
    56 void build(int cur, int l, int r)
    57 {
    58     if(l == r)
    59     {
    60         sum[cur] = tree[cur] = a[l];
    61         return ;
    62     }
    63     int mid = (l + r) >> 1;
    64     build(lson, l, mid);
    65     build(rson, mid + 1, r);
    66     pushup(cur);
    67 }
    68 
    69 int main()
    70 {
    71     int i, op, x, y, cas = 1;
    72     LL ans;
    73     while(scanf("%d", &n) != EOF)
    74     {
    75         for(i = 1; i <= n; i ++)
    76             scanf("%I64d", &a[i]);
    77         build(1, 1, n);
    78         scanf("%d", &m);
    79         printf("Case #%d:\n", cas ++);
    80         while(m --)
    81         {
    82             scanf("%d%d%d", &op, &x, &y);
    83             if(x > y) swap(x, y);   // !
    84             if(op == 0)
    85             {
    86                 update(1, 1, n, x, y);
    87             }
    88             else if(op == 1)
    89             {
    90                 ans = 0;
    91                 query(1, 1, n, x, y, ans);
    92                 printf("%I64d\n", ans);
    93             }
    94         }
    95         putchar('\n');
    96     }
    97     return 0;
    98 }
  • 相关阅读:
    汇编学习--第十天
    linux(03)基础系统优化
    linux(02)基础shell命令
    lf 前后端分离 (6) 支付
    lf 前后端分离 (5) 优惠券
    lf 前后端分离 (4) 价格策略
    lf 前后端分离 (3) 中间建跨域
    lf 前后端分离 (2) 课程数据获取,Serializer的返回
    lf 前后端分离 (1) auth,token认证
    支付宝接口调用总结(1)
  • 原文地址:https://www.cnblogs.com/huangfeihome/p/2710577.html
Copyright © 2020-2023  润新知