본문 바로가기
코딩과 알고리즘

백준 알고리즘 4673번 풀이와 해설

by Cray Fall 2019. 6. 20.

백준 알고리즘 문제

셀프 넘버는 1949년 인도 수학자 D.R. Kaprekar가 이름 붙였다. 양의 정수 n에 대해서 d(n)을 n과 n의 각 자리수를 더하는 함수라고 정의하자. 예를 들어, d(75) = 75+7+5 = 87이다.

양의 정수 n이 주어졌을 때, 이 수를 시작해서 n, d(n), d(d(n)), d(d(d(n))), ...과 같은 무한 수열을 만들 수 있다.

예를 들어, 33으로 시작한다면 다음 수는 33 + 3 + 3 = 39이고, 그 다음 수는 39 + 3 + 9 = 51, 다음 수는 51 + 5 + 1 = 57이다. 이런식으로 다음과 같은 수열을 만들 수 있다.

33, 39, 51, 57, 69, 84, 96, 111, 114, 120, 123, 129, 141, ...

n을 d(n)의 생성자라고 한다. 위의 수열에서 33은 39의 생성자이고, 39는 51의 생성자, 51은 57의 생성자이다. 생성자가 한 개보다 많은 경우도 있다. 예를 들어, 101은 생성자가 2개(91과 100) 있다.

생성자가 없는 숫자를 셀프 넘버라고 한다. 100보다 작은 셀프 넘버는 총 13개가 있다. 1, 3, 5, 7, 9, 20, 31, 42, 53, 64, 75, 86, 97

10000보다 작거나 같은 셀프 넘버를 한 줄에 하나씩 출력하는 프로그램을 작성하시오.

크레이의 해설

셀프넘버라는 개념에 대해서는 처음 알았군요 :)

쉬운 문제측에 속하는 편인데요.

가장 쉬운 풀이법은 10000개의 배열을 정의하고

모두 셀프넘버라고 우선 표시하는 겁니다.

그리고 1부터 10000까지 세면서 수열에 해당하는 숫자를 X표하는 거지요.

그리고 나면 X 표시된 배열요소와 X표되지 않은 배열요소가 남게되는데

X표시되지 않은 배열 요소만 출력하면 됩니다.

메모리 절약을 위해 char 를 사용했는데요.

char 를 사용하면 10,000개당 10,000바이트를 소모하고, int 를 사용하면 10,000개당 20,000 byte 를 소모하게 됩니다.

더욱 메모리를 절약하는 방법으로 bit 연산기법도 있긴 하지만 ( 1250 byte 만 소모 )

데이터가 고작 10,000개밖에 안되기 때문에 char 로 처리하는 방법을 사용했습니다.

부가적으로 배열선언을 10,000개가 아닌 10,001개로 선언했는데요.

10,000개로 배열을 선언하면 배열첨자를 0~9,999까지 사용할 수 있는 반면

10,001개로 배열을 선언하면 배열첨자를 0~10,000까지 사용할 수 있습니다.

크레이는 사람이 알아보기 쉽게 하려는 목적이니 참조해주세요 :)

소스와 주석

 

#include <iostream>
#include <cstring>
#include <string>
using namespace std;

void self_number()
{
	// 계산이 용이하기 10001바이트 배열 선언 ( 첨자 1 ~ 10000 사용 가능 )
	char numbers[10001];
	// 모두 셀프넘버로 우선 체크
	for (int i = 1; i <= 10000; ++i)numbers[i] = 'O';
	// 셀프넘버 아닌 숫자를 X 표시
	for (int i = 1; i <= 10000; ++i)
	{
		// 수열 번호 계산 ( 원래 숫자 + 각 자릿수 숫자 + ... )
		int new_number =
			i +
			i / 10000 +
			(i / 1000) % 10 +
			(i / 100) % 10 +
			(i / 10) % 10 +
			i % 10;

		// 셀프넘버 아닌 숫자를 X 표시, 이 때 10,000번 초과를 검사안하면 
		// 프로그램 메모리 구조가 망가지니 주의가 필요합니다.
		if (new_number <= 10000)numbers[new_number] = 'X';
	}

	// 셀프넘버 출력
	for (int i = 1; i <= 10000; ++i)
		if (numbers[i] == 'O')printf("%d\n", i);
}

int main()
{
	self_number();
	return 0;
}

 

'코딩과 알고리즘' 카테고리의 다른 글

백준알고리즘 1065번 문제 풀이 & 해설  (0) 2019.06.20
아스키 코드표  (2) 2019.06.20
백준알고리즘 1008번 풀이  (0) 2019.06.20
백준 알고리즘 3차 도전  (0) 2019.06.20
백준 알고리즘 2차 도전.  (0) 2019.06.20