문제 소개
시작 값(start)과 끝 값(end) 사이의 숫자 범위가 주어졌을 때, 첫 번째 자릿수와 마지막 자릿수가 같은 숫자가 범위 [start, end] 안에 몇 개 있는지 구하는 것이 목표입니다.
한 자리 숫자는 첫 자리와 마지막 자리가 곧 자기 자신이므로, 범위에 포함되어 있다면 모두 개수에 포함됩니다.
예제로 이해하기
입력 - start = 100, end = 200
출력 - 첫 자리 숫자와 마지막 자리 숫자가 같은 범위 내 숫자의 개수: 10
설명 - 조건을 만족하는 숫자들은 다음과 같습니다.
101, 111, 121, 131, 141, 151, 161, 171, 181, 191
입력 - start = 1, end = 10
출력 - 첫 자리 숫자와 마지막 자리 숫자가 같은 범위 내 숫자의 개수: 9
설명 - 한 자리 숫자는 모두 조건을 만족하므로 1부터 9까지 총 9개가 계산됩니다.
접근 방식
범위 [start, end]에 포함된 한 자리 숫자는 모두 개수에 포함됩니다. 그다음 각 숫자에 대해 첫 자리와 마지막 자리를 비교하는데, 일일이 확인하는 대신 수학적 공식을 활용하면 효율적으로 계산할 수 있습니다. 첫 자리가 마지막 자리보다 크면 count에 8 + val/10을 더하고, 작거나 같으면 9 + val/10을 더합니다. 여기서 val은 range(int val) 함수 호출 시 전달되는 현재 숫자입니다.
- 정수 start와 end를 범위 변수로 받습니다.
- count = range(end) - range(start)로 설정합니다.
- range(int val) 함수는 정수를 입력받아 첫 자리와 마지막 자리가 같은 숫자의 개수를 반환합니다.
- 초기 count는 0으로 설정합니다.
- 마지막 자리는 val % 10으로 구합니다.
- val이 한 자리 숫자(10 미만)라면 val을 그대로 반환합니다.
- while 루프를 사용해 start = val % 10으로 계산하고 val을 10으로 나누어 갱신합니다. 루프가 끝나면 start에는 첫 번째 자릿수가 저장됩니다.
- start <= end이면 count에 9 + set_val / 10을 더합니다.
- start > end이면 count에 8 + set_val / 10을 더합니다.
- 마지막으로 count를 결과로 반환합니다.
예제 코드
#include <iostream>
using namespace std;
int range(int val) {
int count = 0;
int start;
int end = val % 10;
int set_val = val;
if (val < 10) {
return val;
}
end = val % 10;
while (val) {
start = val % 10;
val = val / 10;
}
if (start <= end) {
count = 9 + set_val / 10;
} else {
count = 8 + set_val / 10;
}
return count;
}
int main() {
int start = 10, end = 50;
int count = range(end) - range(start);
cout << "첫 자리 숫자와 마지막 자리 숫자가 같은 범위 내 숫자의 개수: " << count;
return 0;
}
위 코드를 실행하면 다음과 같은 결과가 출력됩니다.
출력 결과
첫 자리 숫자와 마지막 자리 숫자가 같은 범위 내 숫자의 개수: 4
예를 들어 start = 10, end = 50인 경우 조건을 만족하는 숫자는 11, 22, 33, 44로 총 4개입니다. 이처럼 반복문으로 모든 숫자를 하나씩 검사하지 않고도 공식 기반 계산만으로 빠르게 답을 구할 수 있습니다.