思路:
线段树走起。。
写完这题就退役T^T
单点更新的时候直接找到这个点的最近fib,然后维护当前和 和 fib的和
#include<stdio.h> #include<string.h> #include<iostream> #include<math.h> #include<algorithm> #include<queue> #include<map> #include<set> #include<vector> using namespace std; #define L(x) (x<<1) #define R(x) (x<<1|1) #define mod 1000000007 #define N 200000 #define ll long long ll f[100]; inline ll Mid(ll x, ll y){return (x+y)>>1;} ll find(ll x){ ll id = lower_bound(f, f+90, x) - f; if(f[id] == x || id==0)return f[id]; if(f[id] - x >= x - f[id-1]) return f[id-1]; else return f[id]; } struct node{ ll l, r; ll sum, bsum; ll lazy; }tree[N<<2]; void push_down(ll id){ if(tree[id].lazy == 0)return ; tree[id].lazy = 0; if(tree[id].l == tree[id].r) return ; tree[L(id)].sum = tree[L(id)].bsum; tree[R(id)].sum = tree[R(id)].bsum; tree[L(id)].lazy = tree[R(id)].lazy = 1; } void push_up(ll id){ tree[id].sum = tree[L(id)].sum + tree[R(id)].sum; tree[id].bsum = tree[L(id)].bsum + tree[R(id)].bsum; } void build(ll l, ll r, ll id){ tree[id].l = l; tree[id].r = r; tree[id].sum = 0; tree[id].bsum = 0; tree[id].lazy = 0; if(l == r) { tree[id].bsum = find(0); return ; } ll mid = Mid(l, r); build(l, mid, L(id)); build(mid+1, r, R(id)); push_up(id); } ll query(ll l, ll r, ll id){ push_down(id); if(l == tree[id].l && tree[id].r == r) return tree[id].sum; ll mid = Mid(tree[id].l, tree[id].r), ans = 0; if(mid < l) ans = query(l, r, R(id)); else if(r <= mid) ans = query(l, r, L(id)); else ans = query(l, mid, L(id)) + query(mid+1, r, R(id)); push_up(id); return ans; } void updata(ll pos, ll add, ll id){ push_down(id); if(tree[id].l == tree[id].r) { tree[id].sum += add; tree[id].bsum = find(tree[id].sum); return ; } ll mid = Mid(tree[id].l, tree[id].r); if(mid < pos) updata(pos, add, R(id)); else if(pos <= mid) updata(pos, add, L(id)); push_up(id); } void updata2(ll l, ll r, ll id){ push_down(id); if(l == tree[id].l && tree[id].r == r) { tree[id].lazy = 1; tree[id].sum = tree[id].bsum; return ; } ll mid = Mid(tree[id].l, tree[id].r); if(mid < l) updata2(l, r, R(id)); else if(r <= mid) updata2(l, r, L(id)); else { updata2(l, mid, L(id)); updata2(mid+1, r, R(id)); } push_up(id); } ll n, m; int main(){ ll u, v, i, j, op; f[0] = f[1] = 1; for(i = 2; i < 90; i++)f[i] = f[i-1] + f[i-2]; while(cin>>n>>m){ build(1, n, 1); while(m--) { scanf("%I64d %I64d %I64d",&op,&u,&v); if(op==1) updata(u, v, 1); else if(op==2) printf("%I64d\n", query(u, v, 1)); else updata2(u, v, 1); // for(i = 1; i <= n; i++) cout<<query(i, i, 1)<<" "; puts(""); } } return 0; } /* 5 10 2 1 5 3 1 5 2 1 5 1 1 10 2 1 5 3 1 5 2 1 5 4 5 1 1 3 2 1 2 3 2 3 1 2 1 2 1 4 ans: 0 5 15 17 3 */
HDU 4893 Wow! Such Sequence! 水线段树,布布扣,bubuko.com
时间: 2024-11-05 02:24:51