#include <stdio.h> /* printf, scanf, puts, NULL */
#include <stdlib.h> /* srand, rand */
#include <time.h> /* time */
#include <iostream> /* cout, endl */
#include <algorithm> // std::sort, std::find, std::copy
#include <vector> // std::vector
using namespace std;
// 로또조합 순서값(1~8145060)으로 로또조합 알아내기
void getLottoNumberByOrderNumber(int o, int *r)
{
int sum=0,nn=0,a=0,b=0,c=0,d=0,e=0,f=0;
for(a=1; a<=40; a++) {
nn = ((45-a)*(45-a-1)*(45-a-2)*(45-a-3)*(45-a-4)) / (5*4*3*2*1);
if(sum+nn>=o) break;
sum += nn;
}
for(b=a+1; b<=41; b++) {
nn = ((45-b)*(45-b-1)*(45-b-2)*(45-b-3)) / (4*3*2*1);
if(sum+nn>=o) break;
sum += nn;
}
for(c=b+1; c<=42; c++) {
nn = ((45-c)*(45-c-1)*(45-c-2)) / (3*2*1);
if(sum+nn>=o) break;
sum += nn;
}
for(d=c+1; d<=43; d++) {
nn = ((45-d)*(45-d-1)) / (2*1);
if(sum+nn>=o) break;
sum += nn;
}
for(e=d+1; e<=44; e++) {
nn = ((45-e)) / (1);
if(sum+nn>=o) break;
sum += nn;
}
for(f=e+1; f<=45; f++) {
nn = 1;
if(sum+nn>=o) break;
sum += nn;
}
sum++;
r[0] = a;
r[1] = b;
r[2] = c;
r[3] = d;
r[4] = e;
r[5] = f;
}
// 로또 조합이 8145060 조합중 몇번째 조합인지 알아내기
int getOrderNumber(int r[])
{
int sum=0,nn=0,a=0,b=0,c=0,d=0,e=0,f=0;
for(a=1; a<r[0]; a++) {
nn = ((45-a)*(45-a-1)*(45-a-2)*(45-a-3)*(45-a-4)) / (5*4*3*2*1);
sum += nn;
}
for(b=a+1; b<r[1]; b++) {
nn = ((45-b)*(45-b-1)*(45-b-2)*(45-b-3)) / (4*3*2*1);
sum += nn;
}
for(c=b+1; c<r[2]; c++) {
nn = ((45-c)*(45-c-1)*(45-c-2)) / (3*2*1);
sum += nn;
}
for(d=c+1; d<r[3]; d++) {
nn = ((45-d)*(45-d-1)) / (2*1);
sum += nn;
}
for(e=d+1; e<r[4]; e++) {
nn = ((45-e)) / (1);
sum += nn;
}
for(f=e+1; f<r[5]; f++) {
nn = 1;
sum += nn;
}
sum++;
return sum;
}
// 1등 당첨번호+보너스번호를 이용하며 모든 1~5등 조합 생성하기
void make1to5ByWinLotto(int *r, std::vector<int> *v) {
v->clear(); // 결과를 저장할 벡터 변수 clear
for(int i=0; i<7; i++) {
if(r[i]<1 || 45<r[i]) return; // 1등 로또번호+보너스볼의 무결성 체크 #1
if(i==6) break;
for(int j=i+1; j<7; j++) {
if(r[i]==r[j]) return; // 1등 로또번호+보너스볼의 무결성 체크 #2
}
}
int count=0;
int y[6] = {0};
std::vector<int> vv;
// 1등 1개
memcpy(y, r, 6*sizeof(int));
vv.clear();
vv.assign(y, y+6); // 1등 로또 번호에서 6수만 vv 벡터로 복사
std::sort(vv.begin(), vv.end()); // 정렬
std::copy(vv.begin(), vv.end(), y); // 복사
int ordernumber = getOrderNumber(y);
v->push_back(ordernumber);
count++;
// for(int i=0; i<vv.size(); i++)
// cout << " " << vv[i];
// cout << endl;
cout << "count = " << count << endl; // 1 = 1
// 2등 6개
for(int i=0; i<6; i++) {
memcpy(y, r, 6*sizeof(int));
y[i] = r[6]; // 보너스볼
vv.clear();
vv.assign(y, y+6); // 1등 로또 번호에서 6수만 vv 벡터로 복사
std::sort(vv.begin(), vv.end()); // 정렬
std::copy(vv.begin(), vv.end(), y); // 복사
int ordernumber = getOrderNumber(y);
v->push_back(ordernumber);
count++;
// for(int i=0; i<vv.size(); i++)
// cout << " " << vv[i];
// cout << endl;
}
cout << "count = " << count << endl; // 1 + 6 = 7
// 3등 228개 ( 6 * (45-7) = 6*38 = 228 )
for(int i=0; i<6; i++) {
for(int j=1; j<=45; j++) {
if(r[0]==j || r[1]==j || r[2]==j || r[3]==j || r[4]==j || r[5]==j || r[6]==j) continue;
memcpy(y, r, 6*sizeof(int));
y[i] = j; // 당첨번호,보너스번호가 아닌 수를 입력
vv.clear();
vv.assign(y, y+6); // 1등 로또 번호에서 6수만 vv 벡터로 복사
std::sort(vv.begin(), vv.end()); // 정렬
std::copy(vv.begin(), vv.end(), y); // 복사
int ordernumber = getOrderNumber(y);
v->push_back(ordernumber);
count++;
}
}
cout << "count = " << count << endl; // 1 + 6 + 228 = 235
// 4등 11,115개 // 6수중2수를 빼고 + 39수중2수를 뽑는다.
for(int i=0; i<5; i++) {
for(int j=i+1; j<6; j++) { // 6수중 2수를 제거
for(int k=1; k<=44; k++) {
if(r[0]==k || r[1]==k || r[2]==k || r[3]==k || r[4]==k || r[5]==k) continue;
for(int l=k+1; l<=45; l++) {
if(r[0]==l || r[1]==l || r[2]==l || r[3]==l || r[4]==l || r[5]==l) continue;
memcpy(y, r, 6*sizeof(int));
y[i] = k;
y[j] = l;
vv.clear();
vv.assign(y, y+6); // 1등 로또 번호에서 6수만 vv 벡터로 복사
std::sort(vv.begin(), vv.end()); // 정렬
std::copy(vv.begin(), vv.end(), y); // 복사
int ordernumber = getOrderNumber(y);
v->push_back(ordernumber);
count++;
}
}
}
}
cout << "count = " << count << endl; // 1 + 6 + 228 + 11115 = 11350
// 5등 182,780개 // 6수중3수를 빼고 + 39수중3수를 뽑는다.
for(int i=0; i<4; i++) {
for(int j=i+1; j<5; j++) {
for(int k=j+1; k<6; k++) { // 6수중 3수를 제거
for(int l=1; l<=43; l++) {
if(r[0]==l || r[1]==l || r[2]==l || r[3]==l || r[4]==l || r[5]==l) continue;
for(int m=l+1; m<=44; m++) {
if(r[0]==m || r[1]==m || r[2]==m || r[3]==m || r[4]==m || r[5]==m) continue;
for(int n=m+1; n<=45; n++) {
if(r[0]==n || r[1]==n || r[2]==n || r[3]==n || r[4]==n || r[5]==n) continue;
memcpy(y, r, 6*sizeof(int));
y[i] = l;
y[j] = m;
y[k] = n;
vv.clear();
vv.assign(y, y+6); // 1등 로또 번호에서 6수만 vv 벡터로 복사
std::sort(vv.begin(), vv.end()); // 정렬
std::copy(vv.begin(), vv.end(), y); // 복사
int ordernumber = getOrderNumber(y);
v->push_back(ordernumber);
count++;
}
}
}
}
}
}
cout << "count = " << count << endl; // 1 + 6 + 228 + 11115 + 182780 = 194130
std::sort(v->begin(), v->end()); // 정렬
vector<int>::iterator last = std::unique(v->begin(), v->end()); // 중복제거
v->erase(last, v->end()); // 중복제거후 완전히 삭제되지 않은 것들 삭제
//v->erase(std::unique(v->begin(), v->end()), v->end()); // 중복제거 + 찌꺼기삭제 통합
}
int main(int argc, char *argv[])
{
int r[7] = {1,2,3,4,5,6,7}; // 1등 당첨번호 + 보너스번호
std::vector<int> v; // 1등 당첨번호를 기준으로 1~5등에 해당하는 모든 조합을 저장할 벡터 변수
make1to5ByWinLotto(r, &v);
// r=당첨번호+보너스볼=7수 를 이용하여,
// 모든 당첨번호(1~5등)의 orderNumber 를 v 벡터에 저장한다.
// (1등+2등+3등+4등+5등 = 1+6+228+11115+182780 = 194,130)
printf("\n");
printf("%02d,%02d,%02d,%02d,%02d,%02d / %02d\n", r[0],r[1],r[2],r[3],r[4],r[5],r[6]); // 1등 당첨번호+보너스번호 출력
printf("\n");
int r2[6]={0,}; // 로또번호를 저장할 배열
for(int i=0; i<v.size(); i++) {
getLottoNumberByOrderNumber(v[i], r2);
printf("%02d,%02d,%02d,%02d,%02d,%02d\n", r2[0],r2[1],r2[2],r2[3],r2[4],r2[5]);
// 1~5등에 해당하는 모든 조합 출력 (194,130개)
}
printf("\n");
getchar();
return 0;
}
1등 당첨번호+보너스번호를 이용하며 모든 1~5등 조합을 생성하는 소스코드 입니다.
5등은 182,780개 가 존재하게 됩니다.