线段树 (更新区间查询点)秋实大哥与小朋友

╰+哭是因爲堅強的太久メ 2022-06-07 01:48 237阅读 0赞

题目链接:https://vjudge.net/contest/186273\#problem/D

#

D - 秋实大哥与小朋友

Problem Description

秋实大哥以周济天下,锄强扶弱为己任,他常对天长叹:安得广厦千万间,大庇天下寒士俱欢颜。

所以今天他又在给一群小朋友发糖吃。

他让所有的小朋友排成一行,从左到右标号。在接下去的时间中,他有时会给一段区间的小朋友每颗糖,有时会问第x个小朋友手里有几颗糖。

这对于没上过学的孩子来说实在太困难了,所以你看不下去了,请你帮助小朋友回答所有的询问。

Input

第一行包含两个整数n,m,表示小朋友的个数,以及接下来你要处理的操作数。

接下来的mm行,每一行表示下面两种操作之一:

0 l r v : 表示秋实大哥给[l,r]这个区间内的小朋友每人v颗糖

1 x : 表示秋实大哥想知道第x个小朋友手里现在有几颗糖
1≤m,v≤100000,1≤l≤r≤n,1≤x≤n,1≤n≤100000000。

Output

对于每一个1 x操作,输出一个整数,表示第x个小朋友手里现在的糖果数目。

Sample Input

3 4
0 1 3 1
1 2
0 2 3 3
1 3

Sample Output

1
4

代码:

  1. #include<iostream>
  2. #include<cstdio>
  3. using namespace std;
  4. typedef long long ll;
  5. #define N 100000+10
  6. #define lson l,m,rt<<1
  7. #define rson m+1,r,rt<<1|1
  8. ll sum[N<<2],add[N<<2];
  9. struct Node
  10. {
  11. int l,r;
  12. int mid()
  13. {
  14. return (l+r)>>1;
  15. }
  16. }tree[N<<2];
  17. void PushUp(int rt)
  18. {
  19. sum[rt]=sum[rt<<1]+sum[rt<<1|1];
  20. }
  21. void build(int l,int r,int rt)
  22. {
  23. tree[rt].l=l;
  24. tree[rt].r=r;
  25. add[rt]=0;
  26. if(l==r)
  27. {
  28. // scanf("%I64d",&sum[rt]);
  29. sum[rt]=0;
  30. return;
  31. }
  32. int m=tree[rt].mid();
  33. build(lson);
  34. build(rson);
  35. PushUp(rt);//rt从大到小往上返
  36. }
  37. void PushDown(int rt,int m)
  38. {
  39. if(add[rt])
  40. {
  41. add[rt<<1]+=add[rt];
  42. add[rt<<1|1]+=add[rt];
  43. sum[rt<<1]+=add[rt]*(m-(m>>1));
  44. sum[rt<<1|1]+=add[rt]*(m>>1);
  45. add[rt]=0;
  46. }
  47. }
  48. ll query(int l,int r,int rt)
  49. {
  50. if(l==tree[rt].l&&r==tree[rt].r)
  51. {
  52. return sum[rt];
  53. }
  54. PushDown(rt,tree[rt].r-tree[rt].l+1);
  55. int m=tree[rt].mid();
  56. ll res=0;
  57. if(r<=m)
  58. {
  59. res+=query(l,r,rt<<1);
  60. }
  61. else if(l>m)
  62. {
  63. res+=query(l,r,rt<<1|1);
  64. }
  65. else
  66. {
  67. res+=query(l,m,rt<<1);
  68. res+=query(rson);
  69. }
  70. return res;
  71. }
  72. void update(int c,int l,int r,int rt)
  73. {
  74. if(tree[rt].l==l&&tree[rt].r==r)
  75. {
  76. add[rt]+=c;
  77. sum[rt]+=(ll)c*(r-l+1);
  78. return ;
  79. }
  80. if(tree[rt].l==tree[rt].r)
  81. {
  82. return ;
  83. }
  84. PushDown(rt,tree[rt].r-tree[rt].l+1);
  85. int m=tree[rt].mid();
  86. if(r<=m)
  87. {
  88. update(c,l,r,rt<<1);
  89. }
  90. else if(l>m)
  91. {
  92. update(c,l,r,rt<<1|1);
  93. }
  94. else
  95. {
  96. update(c,l,m,rt<<1);
  97. update(c,m+1,r,rt<<1|1);
  98. }
  99. PushUp(rt);
  100. }
  101. int main()
  102. {
  103. int n,m;
  104. while(scanf("%d%d",&n,&m)!=EOF)
  105. {
  106. build(1,n,1);
  107. while(m--)
  108. {
  109. char ch[2];
  110. scanf("%s",ch);
  111. int a,b,c;
  112. if(ch[0]=='1')
  113. {
  114. scanf("%d",&a);
  115. printf("%lld\n",query(a,a,1));
  116. }
  117. else
  118. {
  119. scanf("%d%d%d",&a,&b,&c);
  120. update(c,a,b,1);
  121. }
  122. }
  123. }
  124. return 0;
  125. }

发表评论

表情:
评论列表 (有 0 条评论,237人围观)

还没有评论,来说两句吧...

相关阅读