• HDU4893 Wow! Such Sequence! 线段树


    题意:给你一个序列,其中有三种操作

    1)位置为K 的数+ D

    2)求 l-r 区间和

    3)把 l-r 区间里面的所有数都变为理它最近的斐波纳契数

    解题思路:这个题的区间更新其实可以在单点更新的时候就得出,为节点维护两个 和,一个是 斐波纳契和 一个是正常和 ,再看这个区间有没有被3覆盖,特判一下就行了。

    解题代码:

      1 // File Name: 1007.cpp
      2 // Author: darkdream
      3 // Created Time: 2014年07月29日 星期二 12时49分33秒
      4 
      5 #include<vector>
      6 #include<list>
      7 #include<map>
      8 #include<set>
      9 #include<deque>
     10 #include<stack>
     11 #include<bitset>
     12 #include<algorithm>
     13 #include<functional>
     14 #include<numeric>
     15 #include<utility>
     16 #include<sstream>
     17 #include<iostream>
     18 #include<iomanip>
     19 #include<cstdio>
     20 #include<cmath>
     21 #include<cstdlib>
     22 #include<cstring>
     23 #include<ctime>
     24 #define LL long long 
     25 using namespace std;
     26 #define maxn 100005
     27 struct node{
     28   int is3 ; 
     29   int m , r , l ;  
     30   LL sum ,fsum ; 
     31 }tree[maxn << 2];
     32 LL f[100];
     33 int L(int x)
     34 {
     35    return 2* x;
     36 }
     37 int R(int x)
     38 {
     39    return 2*x + 1; 
     40 }
     41 void pushup(int c)
     42 {
     43    tree[c].sum = tree[L(c)].sum + tree[R(c)].sum ; 
     44    tree[c].fsum = tree[L(c)].fsum + tree[R(c)].fsum ;
     45 }
     46 void  build(int c, int l , int r )
     47 { 
     48      tree[c].l = l ; 
     49      tree[c].r = r; 
     50      tree[c].m = (l+r)/2;
     51      tree[c].is3 = 0 ; 
     52      if(l ==  r)
     53      {
     54         tree[c].sum = 0 ; 
     55         tree[c].fsum = 1 ; 
     56         return ; 
     57      }
     58      build(L(c),l,tree[c].m);
     59      build(R(c),tree[c].m+1,r);
     60      pushup(c);
     61 }
     62 LL ABS(LL x)
     63 {
     64    if(x <= 0 )
     65     return -x; 
     66    else return x; 
     67 }
     68 LL find( LL x )
     69 {
     70     int l = 1 , r = 85 ;
     71     while(l <= r )
     72     {
     73        int m = (l + r)/2; 
     74        if(f[m] > x)
     75        {
     76            r = m - 1;     
     77        }else {
     78            l = m + 1; 
     79        }
     80     }
     81 //    printf("%I64d %I64d
    ",f[l],f[r]);
     82     if(ABS(f[l]-x) < ABS(f[r]-x))
     83     {
     84        return f[l];
     85     }else return f[r];
     86 }
     87 void pushdown(int c)
     88 {
     89     if(tree[c].is3)
     90     {
     91        tree[L(c)].is3 = 1; 
     92        tree[R(c)].is3 = 1;
     93        tree[L(c)].sum = tree[L(c)].fsum;
     94        tree[R(c)].sum = tree[R(c)].fsum;
     95        tree[c].is3 = 0 ; 
     96     }
     97 }
     98 void update(int c, int k , int d)
     99 {
    100      if(tree[c].l == tree[c].r&& tree[c].l == k )
    101      {
    102          tree[c].is3  = 0 ; 
    103          tree[c].sum += d; 
    104          tree[c].fsum = find(tree[c].sum);
    105          return ;                 
    106      }
    107      pushdown(c);
    108      if(k <= tree[c].m) 
    109          update(L(c),k,d);
    110      else update(R(c),k,d);
    111      pushup(c);
    112 }
    113 LL ans = 0 ; 
    114 void get(int c , int l , int r)
    115 {
    116        if(l <= tree[c].l && r >= tree[c].r )
    117        {
    118          ans += tree[c].sum ;
    119          // printf("%I64d
    ",ans);
    120          return ;
    121        }
    122      pushdown(c);
    123      if(l <= tree[c].m)
    124          get(L(c),l,r);
    125      if(r > tree[c].m)
    126          get(R(c),l,r);
    127 }
    128 void change(int c, int l , int r)
    129 {
    130       if(tree[c].is3 == 1)
    131           return ;
    132       if(l <= tree[c].l && r >= tree[c].r)
    133         {
    134               tree[c].is3 = 1;
    135               tree[c].sum = tree[c].fsum;
    136               return ;
    137         }
    138      if(l <= tree[c].m)
    139          change(L(c),l,r);
    140      if(r > tree[c].m)
    141          change(R(c),l,r);
    142      pushup(c);
    143 }
    144 int main(){
    145    int n , m; 
    146    f[0] = 1 ;
    147    f[1] = 1; 
    148    for(int i = 2;i <= 86;i ++)
    149        f[i] = f[i-1] + f[i-2];
    150    while(scanf("%d %d",&n,&m) != EOF)
    151    {
    152        build(1 ,1,n);
    153        int a, b, c  ;
    154        for(int i = 1;i <= m;i ++)
    155        {
    156          int a, b, c  ;
    157          scanf("%d %d %d",&a,&b,&c);
    158          if(a == 1 )
    159          {
    160             update(1,b,c);
    161          }else if(a == 2 ){
    162             ans = 0 ; 
    163             get(1,b,c);
    164             printf("%I64d
    ",ans);    
    165          }else{
    166             change(1,b,c);
    167          }
    168        }
    169    }
    170 return 0;
    171 }
    View Code
    没有梦想,何谈远方
  • 相关阅读:
    算法入门7:分支限界法
    算法入门5:贪心算法
    算法入门4:动态规划
    变量
    Java标识符
    Java中的关键字
    Groovy 配置环境变量
    Robot Framework学习笔记(一)------环境搭建
    关于谷歌浏览器(chrome)的一些好用的插件推荐
    关于UML方法学图中类之间的关系:依赖,泛化,关联
  • 原文地址:https://www.cnblogs.com/zyue/p/3876613.html
Copyright © 2020-2023  润新知