양의 정수 n과 r이 주어져 있을 때, 집합 {1,2,3,….,n}에서 반복을 허용하는 r-조합을 모두 나열하라
#include <stdio.h> int n, r, *set, *out; int count = 0; // 팩토리얼 함수 int factorial(int a, int b) { if (a == 0) return 1; else { int result = 1; for (int i = a; i > b; i--) result *= i; return result; } } // 중복 조합 개수 구하는 함수 int over_combi_num(int n, int r) { int temp = n; // n을 임의로 저장 n = n + r - 1; // h(n,r)=c(n+r-1,r)이므로 인수 n만 n+r-1로 바꿔줌 if (r >= 0 && r <= n) { int denominator, numerator, answer; denominator = factorial(n, n - r); numerator = factorial(r, 0); answer = denominator / numerator; printf("▷ H(%d,%d) = %d\n\n", temp, r, answer); // 출력할 때는 원래 n사용 } } // 중복 조합 나열하는 함수 void over_combination(int start, int end, int index) { // r이 0이면 처리 안 함 if (r == 0) return 0; int i; // end가 0이면 out배열이 다 찼으니 출력 if (end == 0) { for (i = 0; i < start; i++) { printf("%d ", out[i]); } printf("\n"); count++; } // 이 else if는 두 번째 over_combination이 호출돼야지만 실행될 수 있음 // 이게 실행됐다는 것은 set의 마지막 원소까지 out에 주었다는 것이고, // 재귀에 의해 out[r-1]=set[n-1]까지 완료됐다는 것을 의미 // 더 이상 할게 없으니 리턴함 else if (index == n) { return; } else { out[start] = set[index]; // 출력할 내용을 담는 배열 out에 값을 주기 over_combination(start + 1, end - 1, index); // index 고정해서 같은 값 들어가게 설정 // 계속 앞에 있는 것 r개만 주면 안 되니, start는 고정, index를 증가 over_combination(start, end, index + 1); } } void main() { printf("■ 양의 정수 n과 r이 주어져 있을 때, 집합 {1,2,3,....,n}에서 반복을 허용하는 r-조합을 모두 나열하라.\n"); printf("\n□ n을 입력하시오: "); // n 입력 받기 scanf_s("%d", &n); // n값을 이용해서 set 지정 set = (int*)malloc(sizeof(int)*n); for (int i = 0; i < n; i++) set[i] = i + 1; // r만들기 (0~n-1) srand(time(NULL)); r = rand() % n; printf("\n▷ r = %d\n", r); // r이 0일 때 메모리 할당하면 오류 걸리니 패스 if (r != 0) out = (int*)malloc(sizeof(int)*r); // 중복 조합 문제 풀기 over_combi_num(n, r); over_combination(0, r, 0); printf("\n◈ 조합 나열한 것 카운트 = %d\n", count); // 메모리 할당 해제 free(set); free(out); }
확률 코드 패키지
조합 사전 순으로 나열하기
중복 조합 사전 순으로 나열하기
중복 순열 사전 순으로 나열하기
순열 사전 순으로 나열하기