1이 될 때까지
어떠한 수 N이 1이 될 때까지 다음의 두 과정 중 하나를 반복적으로 선택하여 수행하려고 한다
단, 두 번째 연산은 N이 K로 나누어 떨어질 때만 선택할 수 있다
1. N에서 1을 뺀다
2. N을 K로 나눈다
예를 들어 N이 17, K가 4라고 하자.
이 때 1번의 과정을 한 번 수행하면 N은 16이 된다 => 1
이 후 2번의 과정을 두 번 수행하면 N은 1이 된다 => 2
결과적으로 이 경우 전체 과정을 실행한 횟수는 3이 된다. 이는 N을 1로 만드는 최소 횟수이다
N과 K가 주어질 때 N이 1이 될 때까지 1번 혹은 2번의 과정을 수행해야 하는 최소 횟수를 구하는 프로그램을 작성해라
[입력 조건]
- 첫째 줄에 N(2<=N<=100,000)과 K(2<=K<=100,00)가 공백으로 구분되며 각각 자연수로 주어진다.
- 이 때 입력으로 주어지는 N은 항상 K보다 크거나 같다
[출력 조건]
- 첫째 줄에 N이 1이 될 때까지 1번 혹은 2번의 과정을 수행해야 하는 횟수의 최솟값을 출력한다
입력 예시)
25 5
출력 예시)
2
[풀이]
이 문제도 아이디어만 떠올리면 어렵지 않게 해결이 가능하다!
주어진 N에 대해서 '최대한 많이 나누기'를 수행하면 된다
왜냐면 2이상의 수가 주어지면, 그 수로 나누는게 1을 빼는 것보다 훨씬 숫자를 많이 줄일 수 있기 때문이다!
따라서 다음의 과정을 더이상 반복할 수 없을 때까지 반복하면 된다
- N이 K의 배수가 될 때까지 1씩 빼기
- N을 K로 나누기
Q. 근데 위의 풀이가 최적의 해를 보장한다는 것은 어떻게 알지?
A. 사실 당연한거다~!
문제 조건을 보면 K는 항상 2보다 크고, 2보다 큰 수로 숫자를 나누는게 1씩 빼는 것보다 훨씬 빠르게 숫자를 줄일 수 있고, 이는 N이 클수록 더 빨리 줄어든다.
즉, 이게 맞다 이말이다~~
이걸 코드로 구현할 때 반복문을 통해서 배수인지 확인하고 아니면 1을 뺴고, 뭐 이런식으로 구현을 해도 되긴 하지만 난 책에서 알려준 보다 효율적으로 구현하는 방식을 사용해서 구현해볼것이다. 그리고 이건 뭔가 C로 푸는게 더 빠를 것 같아서 C++로 풀어보려고 한다!
C++ 코드)
#include <stdio.h>
#include <iostream>
using namespace std;
int main()
{
int n, k, target, result=0;
cin >> n >> k;
while(1)
{
target=(n/k)*k; //n이 될 수 있는 가장 큰 k의 배수
result += (n-target); //n이 앞에서 구한 k의 배수가 되기 위해 빼준 횟수를 더해준다
n=target;
if(n<k) break; //n을 k로 나눌 수 없는 경우 반복문 탈출
n/=k; //n을 k로 나누기
result++; //한 번 나눴으니까 1 추가
}
result += (n-1); //n이 1이 되기 위해 빼줘야 하는 남은 횟수를 다 더해준다
cout<<result;
return 0;
}
먼저 반복문을 통해 나눌 수 있는 만큼 최대한으로 나눠준다
target을 이용해서 n이 k의 배수가 되기 위해 최소한으로 빼줘야 하는 1의 횟수를 구한다
예를 들어 n=25, k=3이면 target=(25/3)*3=24가 된다
그러면 result에는 25-24=1을 더해준다
25가 24가 되려면 1만 빼주면 되니까 맞게 계산되는 것이다
이런식으로 구현하면 반복문으로 이게 배수인지 아닌지 계속해서 확인하는 것보다 효율적으로 풀 수 있다!
그리고 n이 k보다 작으면 더이상 나눌 수 없으므로 반복문을 탈출하고, 그게 아니면 n을 k로 나눠주고 result에 1을 더해준다 (2번 과정을 한 번 실행했으니깐)
반복문을 탈출하면 n을 더이상 k로 나눌 수 없으니까 남은 방법은 1씩 빼주는 것 뿐이다
그래서 result에 n-1을 더해주는데 이는 n이 1이 되기 위해 빼줘야 하는 횟수이다
이건 단순한 결과 화면~
아 오늘은 좀 일찍 잠들었는데 또 새벽에 깨버려서 그냥 문제 하나 풀었당,,
잠 깬 김에 과제랑 시험공부하다가 마지막 UMC 서버 수업들어야징ㅠㅠ
그럼 빠잉!
'코딩테스트 > 이코테' 카테고리의 다른 글
[이것이 코딩 테스트다 with python] 유튜브 강의 링크 (0) | 2021.12.06 |
---|---|
[CH4 구현] 아이디어를 코드로 바꾸는 구현 1 (0) | 2021.12.05 |
[CH3 그리디] 숫자 카드 게임 (0) | 2021.12.03 |
[CH3 그리디] 큰 수의 법칙 (0) | 2021.12.02 |
[CH3 그리디] 당장 좋은 것만 선택하는 그리디 (0) | 2021.12.01 |
댓글