Cho một dãy a1,a2,…,an. Một đoạn con liên tiếp có dạng al,al+1,…,ar. Ta cũng cho phép chọn đoạn rỗng, có tổng bằng 0.
Có m phép cập nhật. Sau mỗi lần gán một phần tử, hãy tìm tổng lớn nhất của một đoạn con liên tiếp trong toàn bộ dãy hiện tại.
Input
Dòng đầu chứa hai số nguyên n và m.
Dòng thứ hai chứa n số nguyên của dãy ban đầu.
Mỗi dòng trong m dòng tiếp theo chứa hai số kx, nghĩa là gán ak=x.
Output
Sau mỗi cập nhật, in ra một dòng chứa tổng đoạn con liên tiếp lớn nhất. Kết quả không âm vì có thể chọn đoạn rỗng.
Constraints
1≤n,m≤2⋅105.
−109≤ai,x≤109.
1≤k≤n.
Scoring
Subtask 1 (50% số điểm): n,m≤2000.
Subtask 2 (50% số điểm): Không có giới hạn bổ sung.
Example
Test 1
Input
5 4
-3 2 -1 4 -5
1 -2
5 3
2 -6
4 -8
Output
5
8
7
3
Giải thích: Sau hai cập nhật đầu, các đoạn tốt nhất có tổng 5 và 8. Hai trạng thái sau đó có tổng tốt nhất lần lượt là 4+3=7 và đoạn một phần tử 3.
Lời giải tóm tắt
Phân tích: Mỗi node lưu bốn giá trị: tổng toàn đoạn sum, maximum prefix pref, maximum suffix suff, và maximum subarray best; cả ba maximum cho phép đoạn rỗng. Với hai đoạn liên tiếp L,R:
Phân tích:pref = max(L.pref, L.sum + R.pref);
Phân tích:suff = max(R.suff, R.sum + L.suff);
Phân tích:best = max(L.best, R.best, L.suff + R.pref).
Phân tích: Ở lá x, ba maximum đều bằng max(0,x).
Thuật toán: Xây cây bằng công thức trên. Mỗi update thay trạng thái của một lá, gộp lại các node tổ tiên, rồi in best ở gốc.
Chứng minh tính đúng đắn: Mọi prefix và suffix của đoạn ghép thuộc đúng một trong hai dạng thể hiện trong công thức. Một đoạn con tốt nhất hoặc nằm hoàn toàn trong L, hoàn toàn trong R, hoặc cắt ranh giới; trường hợp cuối bắt buộc là suffix của L nối prefix của R. Vì vậy, nếu hai node con đúng thì node cha đúng. Trạng thái lá đúng, nên quy nạp cho thấy bất biến đúng ở mọi node.
Chứng minh tính đúng đắn: Sau cập nhật, chỉ các tổ tiên của lá thay đổi và được tính lại đúng. Gốc quản lý toàn mảng, vì thế best ở gốc luôn là đáp án cần in.
Độ phức tạp: Xây O(n), mỗi cập nhật O(log n), bộ nhớ O(n).