Notice
Recent Posts
Recent Comments
Link
«   2026/02   »
1 2 3 4 5 6 7
8 9 10 11 12 13 14
15 16 17 18 19 20 21
22 23 24 25 26 27 28
Archives
Today
Total
관리 메뉴

hwooo

BOJ (C/C++) 1654번: 랜선 자르기 본문

Study/Algorithm

BOJ (C/C++) 1654번: 랜선 자르기

hwooo 2022. 12. 5. 03:45

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

 

1654번: 랜선 자르기

첫째 줄에는 오영식이 이미 가지고 있는 랜선의 개수 K, 그리고 필요한 랜선의 개수 N이 입력된다. K는 1이상 10,000이하의 정수이고, N은 1이상 1,000,000이하의 정수이다. 그리고 항상 K ≦ N 이다. 그

www.acmicpc.net


풀이

이분 탐색으로 구현. 알고리즘 자체는 어렵지 않으나 사소한 것들을 놓쳐서 오래 걸림.

 

밑에는 풀면서 놓쳤던 오류들

 

- start=0으로 할 때에 mid=0이 될 수 있어 divided by zero 오류 가능성 존재.
   -> start=1로 선언
- start=1로 둘 때 mid 값 계산 시 int형 오버플로우 가능성 존재. (채점 시 시간초과)
   -> start, mid, end 모두 long long 으로 선언

- 답은 가장 작은 입력값보다 작을 수 있음 (ex 2 4 / 4 8  --> ans : 2)
   -> start = 1로 선언

결론 : 되도록이면 다 long long으로 선언하세요...

 

- 잘린 갯수가 int형보다 많을 수 있음 -> long long 선언

- while(start<end)의 조건때문에 start==end일 때의 값이 정답일 때 오류 -> while(start<=end)로 지정

 


코드

#include <stdio.h>
#include <vector>
#include <algorithm>
using namespace std;

vector <int> V;
int length(int K, int N) {
	// 이분탐색을 위한 정렬
	sort(V.begin(), V.end());

	long long int mid, cnt, max = 1, start = 1, end = V[K - 1];

	// Binary Search
	while (start <= end) {
		cnt = 0;
		mid = (start + end) / 2;

		for (int i = 0; i < K; i++)	cnt += (V[i] / mid);

		// 잘린 갯수가 많을 때도 포함해야 함.
		if (cnt >= N) {
			start = mid + 1;			
			if (mid > max) max = mid; // 가장 큰 값 구하기
		}
		else end = mid - 1;
	}
	return max;
}
int main() {
	int N, K, len;
	scanf("%d %d", &K, &N);
	for (int i = 0; i < K; i++) {
		scanf("%d", &len);
		V.push_back(len);
	}
	printf("%d", length(K, N));

	return 0;
}

'Study > Algorithm' 카테고리의 다른 글

BOJ (C/C++) 18111번: 마인크래프트  (0) 2022.12.08
BOJ (C/C++) 10039번: 평균 점수  (0) 2022.12.06
BOJ (C/C++) 15829번: Hashing  (0) 2022.12.05
BOJ (C/C++) 1259번: 팰린드롬수  (0) 2022.12.05
BOJ (C/C++) 12851번: 숨바꼭질 2  (0) 2022.12.04