백준 2042번: 구간 합 구하기 [Gold 1]
https://www.acmicpc.net/problem/2042
2042번: 구간 합 구하기
첫째 줄에 수의 개수 N(1 ≤ N ≤ 1,000,000)과 M(1 ≤ M ≤ 10,000), K(1 ≤ K ≤ 10,000) 가 주어진다. M은 수의 변경이 일어나는 횟수이고, K는 구간의 합을 구하는 횟수이다. 그리고 둘째 줄부터 N+1번째 줄
www.acmicpc.net
문제 풀이
- 이 문제는 구간 합을 구하는 문제로 단순하게 n ~ m을 반복문을 통해 더하게 되면 시간 초과에 걸리게 됩니다.
- 구간 합을 위해 세그먼트 트리나 펜윅 트리를 구현해야 하는데, 저는 펜윅 트리를 구현하여 문제를 풀었습니다.
- 아래의 링크에 세그먼트 트리와 펜윅 트리의 개념에 대해 잘 설명되어 있어서 개념을 숙지해 두시면 좋을 것 같습니다!
- 펜윅 트리 : https://www.acmicpc.net/blog/view/21
펜윅 트리 (바이너리 인덱스 트리)
블로그: 세그먼트 트리 (Segment Tree) 에서 풀어본 문제를 Fenwick Tree를 이용해서 풀어보겠습니다. Fenwick Tree는 Binary Indexed Tree라고도 하며, 줄여서 BIT라고 합니다. Fenwick Tree를 구현하려면, 어떤 수 X
www.acmicpc.net
- 세그먼트 트리 : https://www.acmicpc.net/blog/view/9
세그먼트 트리 (Segment Tree)
글이 업데이트 되었습니다. https://book.acmicpc.net/ds/segment-tree 문제 배열 A가 있고, 여기서 다음과 같은 두 연산을 수행해야하는 문제를 생각해봅시다. 구간 l, r (l ≤ r)이 주어졌을 때, A[l] + A[l+1] + ..
www.acmicpc.net
코드
#include <vector>
#include <cstdio>
using namespace std;
typedef long long ll;
int N, M, K;
void update(vector<ll> &fen_tree, int idx, ll diff) {
while(idx < N+1) {
fen_tree[idx] += diff;
idx += (idx & -idx);
}
}
ll sum(vector<ll> &fen_tree, int idx) {
ll ret = 0;
while(idx > 0) {
ret += fen_tree[idx];
idx -= (idx & -idx);
}
return ret;
}
int main() {
scanf("%d %d %d", &N, &M, &K);
vector<ll> arr(N+1);
vector<ll> fen_tree(N+1);
for(int i=1; i<=N; ++i) {
scanf("%lld", &arr[i]);
update(fen_tree, i, arr[i]);
}
for(int i=0; i<M+K; ++i) {
int a;
scanf("%d", &a);
if(a == 1) {
int b;
ll c;
scanf("%d %lld", &b, &c);
ll diff = c - arr[b];
arr[b] = c;
update(fen_tree, b, diff);
}
else {
int b, c;
scanf("%d %d", &b, &c);
ll res = sum(fen_tree, c) - sum(fen_tree, b-1);
printf("%lld\n", res);
}
}
return 0;
}
실행 결과
'Problem Solving' 카테고리의 다른 글
[c++][java][프로그래머스] 배달 (0) | 2022.03.23 |
---|---|
[c++][python][백준 15649] N과 M (1) (0) | 2022.03.22 |
[c++][프로그래머스] 표 편집 (0) | 2022.03.07 |
[c++][프로그래머스] 거리두기 확인하기 (0) | 2022.03.05 |
[c++][프로그래머스] 숫자 문자열과 영단어 (0) | 2022.03.04 |
댓글