[문제 링크]

 

10610번: 30

문제 어느 날, 미르코는 우연히 길거리에서 양수 N을 보았다. 미르코는 30이란 수를 존경하기 때문에, 그는 길거리에서 찾은 수에 포함된 숫자들을 섞어 30의 배수가 되는 가장 큰 수를 만들고 싶�

www.acmicpc.net


30의 배수가 되기 위한 조건에는 2가지가 있다.

첫째, 반드시 0이 한개 이상 존재해야한다.

둘째, 각 자리수를 모두 더한 값이 3의 배수여야 한다.

 

위 조건을 검사하여 30의 배수가 가능한지 체크한 다음 불가능할 경우 -1 출력, 가능할 경우 N을 내림차순 정렬하여 그대로 출력해주면 원하는 결과를 얻을 수 있다.

 

처음엔 퀵정렬을 이용하여 정렬하였는데 정답은 받았지만 N의 최댓값이 100,000이기 때문에 효율성이 떨어졌다.

정렬할 숫자의 범위가 0~9로 제한되어 있다는 점을 이용하여 계수정렬로 정렬해 효율성을 높였다.


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

void Quick_sort(string& data, int start, int end)
{
	if (start >= end) return;

	int pivot = start;
	int i = start + 1;
	int j = end;

	while (i <= j)
	{
		while (i <= end && data[i] - '0' >= data[pivot] - '0')
			i++;
		while (j > start && data[j] - '0' <= data[pivot] - '0')
			j--;

		if (i > j)
		{
			char temp = data[pivot];
			data[pivot] = data[j];
			data[j] = temp;
		}
		else
		{
			char temp = data[i];
			data[i] = data[j];
			data[j] = temp;
		}
	}
	
	Quick_sort(data, start, j - 1);
	Quick_sort(data, j + 1, end);

	return;
}

void Counting_sort(string& data)
{
	int arr[10] = { 0 };

	int len = data.length();
	for (int i = 0; i < len; i++)
		arr[data[i] - '0']++;

	int here = 0;
	for (int i = 9; i >= 0; i--)
		while (arr[i]--)
			data[here++] = i + '0';
}

int main(void)
{
	string N;
	cin >> N;

	int sum = 0, len = N.size();
	bool zeroCheck = false;
	for (int i = 0; i < len; i++)
	{
		if (N[i] == '0') zeroCheck = true;
		sum += N[i] - '0';
	}

	if (!zeroCheck || sum % 3 != 0)
		cout << -1 << endl;
	else
	{
		//Quick_sort(N, 0, len - 1);
		Counting_sort(N);
		cout << N << endl;
	}

	return 0;
}

알고리즘 200일 프로젝트 - 110 day

'알고리즘 > BOJ' 카테고리의 다른 글

백준 2875번: 대회 or 인턴  (0) 2020.07.27
백준 1541번: 잃어버린 괄호  (0) 2020.07.26
백준 2217번: 로프  (0) 2020.07.26
백준 5585번: 거스름돈  (0) 2020.07.26
백준 1931번: 회의실배정  (0) 2020.07.26

+ Recent posts