※ 글쓴이는 취미로 코딩을 익혀보는 사람이라 정확하지 않은 내용을 담고 있을 수 있다 ※

 

이번에 볼 문제는 백준 17400번 문제인 깃발춤이다.
문제는 아래 링크를 확인하자.

https://www.acmicpc.net/problem/17400 

 

17400번: 깃발춤

첫 번째 줄에는 깃발춤을 진행하는 공연자의 명수인 자연수 N과 상황 변화의 개수인 자연수 Q가 공백으로 구분되어 주어진다. (1 ≤ N ≤ 300,000, 1 ≤ Q ≤ 300,000) 두 번째 줄에는 정수 c1, c2, ..., cN

www.acmicpc.net

이 문제에서는 정수배열과 두 가지 쿼리가 주어진다. 하나는 주어지는 구간에서 홀수번째 수의 합과 짝수번째 수의 합의 차의 절댓값을 구하는 쿼리이고, 다른 하나는 정수배열의 값 하나를 업데이트하는 쿼리이다.

 

항상 홀수번째 수와 짝수번째 수의 차만을 구할 것이므로, 홀수번째 수들을 부호를 반대로 저장하는 세그먼트트리를 이용하면 구간합을 구해 절댓값을 계산하는 것으로 어떤 구간이 주어지더라도 그 구간의 홀수번째 수의 합과 짝수번째 수의 합의 차의 절댓값을 구할 수 있게 된다. 

 

업데이트 시에도 홀수번째 숫자의 변화량의 부호를 반대로 넣어주자.

 

32비트 정수범위를 넘는 수를 다루는 경우가 생길 수 있다는 점에 유의하자.

 

아래는 제출한 소스코드이다.

#include <iostream>
using namespace std;
typedef long long ll;

ll arr[300001];
ll seg[1048577];

ll init(int L, int R, int sI) {
	if (L == R) return seg[sI] = arr[L];
	return seg[sI] = init(L, (L + R) / 2, sI * 2) + init((L + R) / 2 + 1, R, sI * 2 + 1);
}

void update(int L, int R, int qI, int qVal) {
	int sI = 1;
	while (L < R) {
		seg[sI] += qVal;
		int mid = (L + R) / 2;
		if (qI > mid) L = mid + 1, sI = sI * 2 + 1;
		else R = mid, sI = sI * 2;
	}

	seg[sI] += qVal;
}

ll rangesum(int L, int R, int qL, int qR, int sI) {
	if (R < qL || qR < L) return 0;
	if (qL <= L && R <= qR) return seg[sI];
	return rangesum(L, (L + R) / 2, qL, qR, sI * 2) + rangesum((L + R) / 2 + 1, R, qL, qR, sI * 2 + 1);
}

int main() {
	ios::sync_with_stdio(0);
	cin.tie(0);

	int N, Q; cin >> N >> Q;
	for (int i = 1; i <= N; i++) {
		ll& x = arr[i]; cin >> x;
		if (i & 1) x *= -1;
	}

	init(1, N, 1);

	while (Q--) {
		int x; cin >> x;
		if (x == 1) {
			int L, R; cin >> L >> R;
			cout << abs(rangesum(1, N, L, R, 1)) << '\n';
		}
		else {
			int qI, qVal; cin >> qI >> qVal;
			if (qI & 1) update(1, N, qI, -qVal);
			else update(1, N, qI, qVal);
		}
	}
}
728x90

'BOJ' 카테고리의 다른 글

[BOJ 15337 // C++] Starting a Scenic Railroad Service  (0) 2022.01.04
[BOJ 1536 // C++] Dance, Dance  (0) 2022.01.03
[BOJ 10976 // C++] 피난  (0) 2022.01.01
[BOJ 1739 // C++] 도로 정비하기  (0) 2021.12.31
[BOJ 3747 // C++] 완벽한 선거!  (0) 2021.12.30

+ Recent posts