題目描述
食堂有n個打飯視窗,現在正到了午飯時間,每個視窗都排了很多的學生,而且每個視窗排隊的人數在不斷的變化。
現在問你第i個視窗到第j個視窗一共有多少人在排隊?
輸入輸入的第一行是乙個整數t,表示有t組測試資料。
每組輸入的第一行是乙個正整數n(n<=30000),表示食堂有n個視窗。
接下來一行輸入n個正整數,第i個正整數ai表示第i個視窗最開始有ai個人排隊。(1<=ai<=50)
接下來每行有一條命令,命令有四種形式:
(1)add i j,i和j為正整數,表示第i個視窗增加j個人(j不超過30);
(2)sub i j,i和j為正整數,表示第i個視窗減少j個人(j不超過30);
(3)query i j,i和j為正整數,i<=j,表示詢問第i到第j個視窗的總人數;
(4)end 表示結束,這條命令在每組資料最後出現;
每組資料最多有40000條命令。
輸出對於每組輸入,首先輸出樣例號,佔一行。
然後對於每個query詢問,輸出乙個整數,佔一行,表示詢問的段中的總人數,這個數保持在int以內。
樣例輸入 copy
1101 2 3 4 5 6 7 8 9 10
query 1 3
add 3 6
query 2 7
sub 10 2
add 6 3
query 3 10
end
樣例輸出 copy
case 1:63359這一題可以通過線段樹來解決
#include#include#include
#include
#include
#include
using
namespace
std;
const
int size=30005
;struct
segmenttree t[size*4];//
struct陣列儲存線段樹
inta[size];
void build(int p,int l,int
r)//
葉節點
int mid=(l+r)/2;//
折半 build(p*2,l,mid);//
左子節點[l,mid],編號p*2
build(p*2+1,mid+1,r); //
右子節點[mid+1,r],編號p*2+1
t[p].dat=t[p*2].dat+t[p*2+1].dat;//
從下往上傳遞資訊
}int ask(int p,int l,int r)//
查詢區間和
void change(int p,int x,int v,int xx)
int mid=(t[p].l+t[p].r)/2
;
if(x<=mid) change(p*2,x,v,xx);//
x屬於左半區間
else change(p*2+1,x,v,xx); //
x屬於右半區間
t[p].dat=t[p*2].dat+t[p*2+1].dat;//
從下往上更新資訊
}int
main()
}return0;
}
通過線段樹可以快速進行單點更新 和 區間求和相當於乙個非常巧妙的遞迴
先從上往下到葉節點
再將葉節點往上累加
再從下回到起點
至於線段樹的講解
可以先看一下下面的講解哦
二叉樹習題之重建二叉樹
對於給定前序和中序的重建方法。1 前序的第乙個元素一定是樹的根節點,在中序集合中找到此元素,那麼該元素的左面即為根的左子樹,右面為右子樹。2 找到前序的第二個元素,重複上面的步驟。自寫程式的效率大概為 n n 2 或最大的那個元素 這點很坑,斟酌改掉 目前沒發現更快的寫法 自己寫 結果以連續記憶體的...
二叉樹 二叉查詢樹
構建二叉樹,判斷是否為二叉查詢樹,遞迴先序遍歷,非遞迴中序遍歷 include include include include using namespace std 二叉樹結點 struct treenode 鍊錶結點 struct listnode struct tempnodetempnode...
二叉樹 二叉查詢樹
二叉樹 binary tree 一種樹型結構,每個節點最多擁有兩個節點。如下圖 幾種型別的二叉樹 1.full binary tree 每個節點的孩子數 是 0 或者 2.對高度沒有要求。如下圖 2.perfect binary tree 這個就是最完美的樹,顧名思義,所有葉子節點都有相同的深度,並...