http://acm.hdu.edu.cn/showproblem.php?pid=1394

题意:

给定一个数组a,一开始数组里面的元素都是0,现在有三个操作:

操作1:给第k个数字加上d.

操作2:查询区间[l,r]的和.

操作3:改变区间[l,r]的每个数为最接近的斐波那契数列.其中斐波那契数列的f0=1,f1=1.

题解:

这题是单点更新+区间求和+区间更新,我们知道区间求和为了节省一点时间用的是懒惰标记来给每个被更改过的区间打上标记,而当我们需要计算这个区间的时候才将标记下推,使得值更新.

所以对于操作1的话,当我们更新单点的值得时候,由于当前区间在之前可能经历过区间的更改,所以我们需要维护两个数组来.第一个数组sum1用来维护所需要的输出的和,第二个数组sum2用来维护的是经过操作3之后的当前区间的和.

所以对于操作1的时候,需要判断一下该点有没有懒惰标记,如果有的话,该点的值用的就是经过操作3的sum2的值来更改,否则直接更改sum1的值.

AC代码:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
typedef unsigned long long ull;
int dir[][]={{,},{,},{,},{,-},{-,},{-,-},{,-},{-,}};
#define pi acos(-1)
#define ls rt<<1
#define rs rt<<1|1
#define me0(s) memset(s,0,sizeof(s))
#define me1(s) memset(s,1,sizeof(s))
#define mef(s) memset(s,-1,sizeof(s))
#define meinf(s) memset(s,inf,sizeof(s))
#define llinf 1e18
#define inf 1e9
const int N=1e5+;
ll fab[N];
int n,m;
ll lazy[N*]; //lazy表示该区间的数要更改为斐波那契
ll a[N],sum1[N*],sum2[N*];//sum1表示原来的和,sum2表示更改后的值
void init(){
fab[]=fab[]=;
for(int i=;i<=;i++){
fab[i]=fab[i-]+fab[i-];
}
}
ll find_fab(ll x){
ll ans=fab[];
ll c=abs(fab[]-x);
for(int i=;i<=;i++){
if(abs(x-fab[i])<c){
c=abs(x-fab[i]);
ans=fab[i];
}
}
return ans;
}
void pushup(int rt){
sum1[rt]=sum1[ls]+sum1[rs];
sum2[rt]=sum2[ls]+sum2[rs];
}
void pushdown(int rt){
if(lazy[rt]){
lazy[ls]=lazy[rs]=lazy[rt];
lazy[rt]=;
sum1[ls]=sum2[ls];
sum1[rs]=sum2[rs];
}
}
void build(int l,int r,int rt){
if(l==r){
sum2[rt]=;//初始状态所有数据为0,距离0最近的菲波那切数是1
return ;
}
int m=(l+r)/;
build(l,m,ls);
build(m+,r,rs);
pushup(rt);
}
void update1(int l,int r,int p,int c,int rt){
if(l==r){
if(lazy[rt]) sum1[rt]=sum2[rt]+c;
else sum1[rt]+=c;
sum2[rt]=find_fab(sum1[rt]);//更新sum1,sum2也要改变
lazy[rt]=;
return ;
}
pushdown(rt);
int m=(l+r)/;
if(p<=m) update1(l,m,p,c,ls);
if(p>m) update1(m+,r,p,c,rs);
pushup(rt);
}
void update2(int L,int R,int l,int r,int rt){
if(L<=l&&R>=r){
sum1[rt]=sum2[rt];
lazy[rt]=;
return ;
}
pushdown(rt);
int m=(l+r)/;
if(L<=m) update2(L,R,l,m,ls);
if(R>m) update2(L,R,m+,r,rs);
pushup(rt);
}
ll query(int L,int R,int l,int r,int rt){
if(L<=l&&R>=r){
return sum1[rt];
}
pushdown(rt);
int m=(l+r)/;
ll ans=;
if(L<=m) ans+=query(L,R,l,m,ls);
if(R>m) ans+=query(L,R,m+,r,rs);
return ans;
}
int main(int argc, char * argv[]){
init();
while(scanf("%d%d",&n,&m)!=EOF){
me0(sum1);
me0(lazy);
build(,n,);
while(m--){
int op,l,r;
scanf("%d%d%d",&op,&l,&r);
if(op==){
update1(,n,l,r,);
}
else if(op==){
printf("%lld\n",query(l,r,,n,));
}
else{
update2(l,r,,n,);
}
}
}
return ;
}

hdu-4893的更多相关文章

  1. 2014联合三所学校 (HDU 4888 HDU 4891 HDU 4893)

    HDU 4891 The Great Pan 注册标题  他怎么说,你怎么样  需要注意的是乘法时,它会爆炸int 代码: #include<iostream> #include<c ...

  2. HDU 4893 Wow! Such Sequence! (线段树)

    Wow! Such Sequence! 题目链接: http://acm.hdu.edu.cn/showproblem.php?pid=4893 Description Recently, Doge ...

  3. hdu 4893 Wow! Such Sequence!

    http://acm.hdu.edu.cn/showproblem.php?pid=4893 三种操作: 1 k d - "add" 2 l r - "query sum ...

  4. HDU 4893 线段树的 点更新 区间求和

    Wow! Such Sequence! Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Oth ...

  5. hdu 4893 Wow! Such Sequence!(线段树)

    题目链接:hdu 4983 Wow! Such Sequence! 题目大意:就是三种操作 1 k d, 改动k的为值添加d 2 l r, 查询l到r的区间和 3 l r. 间l到r区间上的所以数变成 ...

  6. HDU 4893 Wow! Such Sequence!(2014 Multi-University Training Contest 3)

    题意: 有三种操作: 1 x y: 表示给x位置加上y 2 x y:查询[x,y]的区间和 3 x y:将 [x,y] 区间上的数变为最接近的 Fibonacci. 思路: 1 操作按正常单调更新,区 ...

  7. HDU 4893 线段树

    比赛时太大意,斐波拉契数列开小了. 题目大意:1个序列,3种操作,改变序列某个数大小,将序列中连续的一段每个数都变成其最近的斐波拉契数,以及查询序列中某一段的数之和. 解题思路:维护add[]数组表示 ...

  8. HDU 4893 Wow! Such Sequence!(2014年多校联合 第三场 G)(线段树)

    磨了一天的线段树,不能说完全搞清楚,只能说有一个大概的了解,靠着模板才把这道题A了,只能说太弱~~! 题意: 初始时有一字符串,全为0. 三种操作: 1 k d - add  把d加到第k个数上去2 ...

  9. 线段树 + 区间更新: HDU 4893 Wow! Such Sequence!

    Wow! Such Sequence! Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Oth ...

  10. HDU 4893 Wow! Such Sequence! (树状数组)

    题意:给有三种操作,一种是 1 k d,把第 k 个数加d,第二种是2 l r,查询区间 l, r的和,第三种是 3 l r,把区间 l,r 的所有数都变成离它最近的Fib数, 并且是最小的那个. 析 ...

随机推荐

  1. vue中axios的封装以及简单使用

    一.axios的封装 在vue中为了使用axios使用方便,不需要每一个模块进行导入,就需要对其进行封装: 1.新建http.js模块 import axios from 'axios' // 设置基 ...

  2. PKUSC订正

    Day1 T2:最大前缀和 枚举答案集合(不直接枚举答案数,相当于状态的离散化),这个集合成为答案当且仅当存在方案使得答案集合的排列后缀和>=0(如果<0就可以去掉显然更优),答案补集的前 ...

  3. Linux环境相关

    Linux环境相关 CentOS7网络配置静态ip CentOS7查看ip地址:以前是ifconfig,现在变成了 ip addr 当然这是配置好环境最后的结果,刚装好系统时时没有下面的ens33的相 ...

  4. NX二次开发-设置WCS显示UF_CSYS_set_wcs_display

    NX9+VS2012 #include <uf.h> #include <uf_csys.h> UF_initialize(); //设置WCS显示 //1显示WCS, 0不显 ...

  5. mysql 导出导入数据 -csv

    MySql数据库导出csv文件命令: mysql> select first_name,last_name,email from account into outfile 'e://output ...

  6. 简述MapReduce数据流

    目前it基本都是一个套路,获得数据然后进行逻辑处理,存储数据. 基本上弄清楚整个的数据流向就等于把握了命脉. 现在说说mapreduce的数据流 1.首先数据会按照TextInputFormat按照特 ...

  7. delphi基础篇之项目文件

    delphi基础篇之项目文件   program Teacher2018; uses   Forms, Unit1 in 'Unit1.pas' {Form1}, Unit2 in 'Unit2.pa ...

  8. 中断控制及basepri 与 basepri_max

    1.总开关 每个CPU有一个中断总开关.通过CPU中断控制寄存器实现.Cortex-M的中断控制寄存器包括:FAULTMASK.PRIMASK.BASEPRI.BASEPRI_MAX.总开关的本质是变 ...

  9. 洛谷P3916 图的遍历

    题目链接:https://www.luogu.org/problemnew/show/P3916 题目大意 略. 分析 以终为始,逆向思维. 代码如下 #include <bits/stdc++ ...

  10. 剑指offer——34之字打印二叉树

    题目描述 请实现一个函数按照之字形打印二叉树,即第一行按照从左到右的顺序打印,第二层按照从右至左的顺序打印,第三行按照从左到右的顺序打印,其他行以此类推.   题解: 与上道题没区别,就是在存入数据时 ...