반응형
리뷰
https://www.acmicpc.net/problem/24938
Solve.ac에 있는 주간문제를 알고리즘 분류를 안보고 풀어보았다. 그런데 그리디 알고리즘 문제가 나왔군
전역 변수
- n : 방의 개수를 저장할 변수
- total : 키트의 총 개수를 저장할 변수
- ans : 발생하는 혼잡도의 총 값을 저장하고 출력할 변수
- kit : 각 방마다 보유한 키트의 개수를 입력 받을 정수형 배열, 크기는 20만으로 초기화 한다.
- Node : 키트를 더 많이 갖고 있는 방에서 남는 키트 정보를 저장할 구조체
- deq : 방의 순서대로 남은 키트를 수거하여 갖고 있는 키트를 관리할 Node타입 덱
함수
없음
문제풀이
- n값을 입력 받고 n번의 for문을 순회해 준다.
- kit의 i번째 인덱스에 해당 방이 보유한 키트 수를 입력받아 준다.
- total변수에 각 방이 보유한 키트의 수를 더해 총 키트 수를 초기화해 준다.
- div변수에 total / n한 값을 받는다, 이는 각 방에 존재해야할 키트의 개수이다.
- 다시 n번의 for문을 순회하고 div개 초과 키트를 보유한 방에서 남는 키트와 방번호를 deq에 추가해 준다.
- 다시 n번의 for문을 순회하고 div개 미만 키트를 보유한 방이 만나면 deq에서 꺼내 키트를 분배해 준다.
- deq이 비지 않았고, i번째 방의 키트가 아직 div보다 작다면 계속해서 수행해 준다.
- deq의 맨 앞 요소를 꺼내주고, 모자란 만큼 키트를 방에 전달한다.
- 만약 키트를 충분히 전달했는데 아직 개수가 남았다면 deq의 앞쪽에 남은 키트와 방번호를 추가해 준다.
- 모든 반복 작업을 마친 후 ans에 저장된 값을 출력해 준다.
참고 사항
우선순위 큐를 사용해도 될 것 같다, pq를 쓴다면 인덱스 오름차순으로 정렬하면 될듯?
정답 코드
#include<iostream>
#include<deque>
#define ll long long
using namespace std;
ll n, total, ans;
ll kit[200000];
struct Node{
ll cnt, idx;
};
deque<Node> deq;
int main() {
ios::sync_with_stdio(0);
cin.tie(0);
cin >> n;
for (int i = 0; i < n; i++) {
cin >> kit[i];
total += kit[i];
}
ll div = total / n;
for (int i = 0; i < n; i++) {
if (kit[i] > div) deq.push_back({ kit[i] - div, i });
}
for (int i = 0; i < n; i++) {
if (kit[i] < div) {
while (!deq.empty() && kit[i] < div) {
Node node = deq.front(); deq.pop_front();
ll cnt = node.cnt, idx = node.idx;
ll need = min(div - kit[i], cnt);
kit[i] += need;
kit[idx] -= need;
ans += need * (abs(i - idx));
cnt -= need;
if (cnt) deq.push_front({ cnt, idx });
}
}
}
cout << ans;
}
728x90
반응형
'알고리즘 공부 > C++' 카테고리의 다른 글
[S4] 백준 24465번 데뷔의 꿈 C++ 구현, 정렬 (1) | 2024.10.24 |
---|---|
[L3] 프로그래머스 베스트앨범 C++ 해시맵, 우선순위 큐 (0) | 2024.10.24 |
[P3] 백준 13505번 두 수 XOR C++ 트라이, 트리 (0) | 2024.10.22 |
[G1] 백준 17435번 합성함수와 쿼리 C++ LCA, 최소 공통 조상, 희소 배열 (1) | 2024.10.22 |
[G4] 백준 1477번 휴게소 세우기 C++ 이분 탐색, 매개 변수 탐색 (0) | 2024.10.22 |