※ 글쓴이는 취미로 코딩을 익혀보는 사람이라 정확하지 않은 내용을 담고 있을 수 있다 ※

 

이번에 볼 문제는 백준 10244번 문제인 최대공약수들이다.
문제는 아래 링크를 확인하자.

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

 

10244번: 최대공약수들

n개의 수로 이루어진 수열 A가 주어질 때, 1≤lo≤hi≤n의 정의역을 가지는 함수 f(lo,hi)는 Alo부터 Ahi까지 모든 원소들의 최대공약수로 정의된다. lo와 hi는 수열의 원소가 아닌 인덱스라는 점에 주

www.acmicpc.net

크기가 1 이상 100 이하의 정수들로 이루어진 길이 10만의 수열이 주어질 때, 이 수열의 contiguous한 부분수열의 숫자들이 이루는 gcd로 나올 수 있는 숫자의 가짓수를 묻는 문제이다.

 

이 수열을 구성하고 있는 숫자의 범위가 굉장히 좁다는 점을 눈여겨보자.

 

특히, 이 수열에서 나올 수 있는 gcd의 경우의 수는 1 이상 100 이하의 정수 100가지 뿐이라는 점을 관찰하자.

따라서, 길이 10만의 수열을 100번 순회하면서(1000만번의 연산), 각 순회마다 그 숫자를 gcd로 하는 contiguous한 부분수열이 있는지를 확인하는 것으로 문제를 통과할 수 있을 것이라 짐작했다. (테스트케이스의 수가 주어져있지 않으므로...)

 

아래는 제출한 소스코드이다.

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

int gcd(int x, int y) {
	if (y == 0) return x;
	return gcd(y, x % y);
}

int arr[100000];
int visited[101];

int main() {
	ios::sync_with_stdio(0);
	cin.tie(0);

	int N; cin >> N;
	while (N) {
		memset(visited, 0, sizeof(visited));

		for (int i = 0; i < N; i++) {
			int& x = arr[i];
			cin >> x;
			visited[x] = 1;
		}

		int g;
		int cnt = 0;
		for (int k = 1; k <= 100; k++) {
			if (visited[k]) {
				cnt++;
				continue;
			}
			g = arr[0];
			for (int i = 1; i < N; i++) {
				g = gcd(g, arr[i]);
				if (g == k) {
					visited[k] = 1;
					cnt++;
					break;
				}
				else if (g % k) g = arr[i];
			}
		}

		cout << cnt << '\n';
		cin >> N;
	}
}
728x90

'BOJ' 카테고리의 다른 글

[BOJ 11635 // C++] Wipe Your Whiteboards  (0) 2021.12.01
[BOJ 14565 // C++] 역원(Inverse) 구하기  (0) 2021.11.30
[BOJ 11414 // C++] LCM  (0) 2021.11.28
[BOJ 4779 // C++] 칸토어 집합  (0) 2021.11.27
[BOJ 17829 // C++] 222-풀링  (0) 2021.11.26

+ Recent posts