discription:
已知乙個數列,你需要進行下面兩種操作:
將某乙個數加上 x
求出某區間每乙個數的和
input:
1 x k 含義:將第 x 個數加上 k
2 x y 含義:輸出區間 [x,y] 內每個數的和
output:
所有2操作的結果.
solution:
引入lowbit運算:例如\(44\ =\ (101100)_2\), 其lowbit即為最低位的\(1\)及其後(可能)的\(0\), 即\((100)_2\)即4.
應該如何計算呢? 考慮簡單的位運算:\(lowbit(x)=x\&\sim x+1, 即(101100)_2 \rightarrow(010011)_2\rightarrow (010100)_2\rightarrow (000100)_2\)
也就是\(4\). 在計算機中整數儲存的方式就是二進位制, 所以根據補碼, 取反加一就是取負號. 所以有如下實現:
inline int lowbit(const int& x)
建立t陣列, 初始化為: \(t[x]=\sum_^arr[x]\)
\(prop2:t[x]的father為t[x+lowbit(x)]\)
\(prop3:treedepth=\lceil\rceil+1\)
\(prop4:lowbit(lowbit(x))=lowbit(x)\)
**中實現了:
單點修改
遞迴尋找下標為\(x以及x+lowbit(x)的所有段和t[i]都要修改\)
區間查詢
字首和\(s=\sum_t[x] [x\leftarrow x-lowbit(x)]\)
code:
#includeclass binarray
~binarray()
inline int lowbit(const int& x) const
void in()
} inline void add(int x, const int& k)
inline int ask(const int& l, const int& r)
private:
int* arr;
int* t;
int size;
};int main()
}
binarray是我自己起的名字, 結合了binary和array. luogu3374 模板 樹狀陣列 1
題面 已知乙個數列,你需要進行下面兩種操作 1.將某乙個數加上x 2.求出某區間每乙個數的和 題解1單點修改 區間查詢。關於樹狀陣列的理解,補上一點。位運算的操作其實對應的就是任意乙個整數在二進位制下都可以被拆分為2 i 2 i 1 這種形式,所以將1 n的區間也拆成這種好幾個長為2 i的和並加起來...
洛谷 3374 模板 樹狀陣列 1
題目描述 如題,已知乙個數列,你需要進行下面兩種操作 1.將某乙個數加上x 2.求出某區間每乙個數的和 輸入輸出格式 輸入格式 第一行包含兩個整數n m,分別表示該數列數字的個數和操作的總個數。第二行包含n個用空格分隔的整數,其中第i個數字表示數列第i項的初始值。接下來m行每行包含3個整數,表示乙個...
P3374 模板 樹狀陣列 1
如題,已知乙個數列,你需要進行下面兩種操作 1.將某乙個數加上x 2.求出某區間每乙個數的和 輸入格式 第一行包含兩個整數n m,分別表示該數列數字的個數和操作的總個數。第二行包含n個用空格分隔的整數,其中第i個數字表示數列第i項的初始值。接下來m行每行包含3個整數,表示乙個操作,具體如下 操作1 ...