본문 바로가기

공부/알고리즘

(6)
확장 유클리드 호제법 (Extended Euclidean Algorithm) 1. 정의 확장 유클리드 호제법은 두 정수 $a, b$에 대해 $GCD(a, b) = d$라고 했을 때, $ax + by = d$를 만족하는 $x, y$를 찾을 때 이용되는 알고리즘이다. 확장 유클리드 호제법에 대해 공부하기 전에 유클리드 호제법과 베주 항등식이 무엇인지 먼저 알아보자. 1) 유클리드 호제법 두 정수 $a, b$에 대하여 최대공약수 $GCD(a, b)$를 빠르게 찾는 알고리즘이다. $a$를 $b$로 나눈 나머지를 $r$이라고 할 때, $GCD(a, b) = GCD(b, r)$이 성립하는데 유클리드 호제법은 이 성질을 이용한다. 아래와 같이 한 숫자에서 다른 숫자를 계속 나누어서 나머지가 0이 될 때까지 위 성질을 이용하면 몇 번의 연산만으로 $GCD(a, b)$를 구할 수 있다. $a$를..
백트래킹 (Backtracking) 백트래킹이란 경로를 탐색하다가 올바르지 않은 경로라면 계속해서 탐색하는 것이 아니라 이전 단계로 돌아가 다시 올바른 경로를 향해 찾아가는 알고리즘이다. 모든 경로를 탐색하는 알고리즘인 DFS를 이용하지만, 조건에 맞지 않는 경로는 제외시킨다는 점에서 조금 더 효율적이다. 여기서 경로를 제외시키는 것을 가지치지(pruning)이라고 한다. 가지치기를 하기 위한 조건을 얼마나 잘 설정하느냐에 따라 시간복잡도가 천차만별이다. 백트래킹 알고리즘은 대표적으로 순열, 조합을 구하는 것에 이용된다. 1. 순열 (중복x) ● 코드 #include #include #include #include #include #include #include #include #include #include #include #includ..
카운팅 정렬 (Counting Sort) ● 코드 #include #include #include #include using namespace std; using ll = long long; using ii = pair; vectorarr(10001); int main() { // 입력 int N; cin >> N; for (int i = 0; i > n; // 카운팅 정렬 arr[n]++; } // 출력 for (int i = 0; i < arr.size(); i++) { if (arr[i]) { while (arr[i]--) cout
병합 정렬 (Merge Sort) ● 코드 #include #include #include #include using namespace std; using ll = long long; using ii = pair; vectorarr(1000000); vectortemp(1000000); void mergesort(int start, int end); // 분할 void merge(int start, int mid, int end); // 정복 int main() { // 입력 int N; cin >> N; for (int i = 0; i > arr[i]; // 병합 정렬 mergesort(0, N - 1); // 출력 for (int i = 0; i < N; i++) cout
삽입 정렬 (Insertion Sort) ● 코드 #include #include #include #include using namespace std; using ll = long long; using ii = pair; int main() { // 입력 int N; cin >> N; vectorarr(N); for (int i = 0; i > arr[i]; // 삽입 정렬 for (int i = 1; i < N; i++) { int temp = arr[i]; int idx = i - 1; while (0
버블 정렬 (Bubble Sort) ● 코드 #include #include #include #include using namespace std; using ll = long long; using ii = pair; int main() { // 입력 int N; cin >> N; vectorarr(N); for (int i = 0; i > arr[i]; // 버블 정렬 for (int i = 0; i arr[j]) swap(arr[i], arr[j]); } } // 출력 for (int i = 0; i < N; i++) cout