[C언어-막코딩] 17장 배열(실습편)
- 다운 사이트 : https://sourceforge.net/projects/orwelldevcpp/
- 웹컴파일러 : https://www.tutorialspoint.com/compile_c_online.php
오늘은 다음 진도를 나아 갈까 고민하다가 배열을 이용한 코딩 실습 시간을 갖는게 좋을 것 같아서 진도가 아닌 복습 차원으로 배열을 이용한 코딩 실습을 해보도록 하겠습니다.
1. 랜덤 로또 번호 생성기
재밌는 주제로 로또 번호를 랜덤으로 만들어 보는 시간을 갖도록 하겠습니다.
로또 번호는 총 6개로 구성된 랜덤 숫자입니다. 6개의 데이터를 저장하기 위해서는 배열 변수를 사용해야 겠죠. 그리고 랜덤 숫자이니 6개의 배열 변수에 랜덤 숫자를 만들어서 저장하는 코딩문을 만들어야 겠죠. 이 코딩을 하기 위해서는 배열과 한쌍을 이루는 for문을 이용하여 로직을 짜면 되겠죠.
제일 먼저 로또 랜덤번호를 만들기 위해서는 랜덤 함수를 사용해야 합니다.
랜덤함수 사용
#include <time.h>
srand(time(NULL)) : 랜덤함수 초기화
rand() : 랜덤 함수
srand()함수로 우선 랜덤 초기화 작업을 수행 해야 합니다. 그 이유는 srand()함수가 없다면 초기 고정된 숫자에서 rand()함수의 숫자가 추출됩니다. 프로그램을 실행 하는 첫 숫자는 무조건 동일한 값을 출력하게 됩니다. 랜덤 숫자가 아닌 셈이죠. 그래서 srand()함수를 이용하여 초기값을 현재 time()시간을 기준으로 초기화가 이루어지게 함으로서 프로그램을 실행 할 때마다 첫 수자가 현재시간값에 영향을 받어 무작위 숫자가 출력되게 됩니다.
범위 랜덤숫자 추출
val=(rand()%45)+1;
rand()함수에서 추출한 값에서 45로 나눈 나머지값은 0~44까지의 범위의 무작위 숫자를 얻습니다. 로또는 1~45까지니 0~44까지 범위에서 +1을 함으로서 1~45까지의 무작위 숫자를 얻게 됩니다.
배열 변수의 랜덤숫자 저장
int Lotto[6];
for(i=0;i<6;i++){
Lotto[i]=(rand()%45)+1;
}
Lotto[6] 배열변수에 6개의 랜덤 숫자가 저장되겠죠. 랜덤 로또 번호 생성기 프로그램이 완성 되었네요라고 생각 할 수 있지만 알아야 할 것은 6개의 숫자가 서로 다른 숫자여야 합니다. 중복 숫자가 나오게 되면 6개 미만의 숫자가 나오겠지요.
중복 숫자 제외
for(i=0;i<6;i++){
Lotto[i]=(rand()%45)+1;
for(j=0;j<i;j++){
if(Lotto[i]==Lotto[j]){
i--;
break;
}
}
}
for문의 각 라인을 잘 살펴 봐주세요. for문 i의 겨우는 6번 루프를 돌게 됩니다. 그리고 i번째 Lotto[i]변수에 1~45사이의 무작위 숫자를 저장하게 됩니다. 그런데 또 안에 for문 j가 있죠. 두번째 for문은 현재 추출한 값이 지금까지 추출한 숫자들과 비교하여 중복되는지 체크하는 코딩문입니다.
언뜻 잘 이해가 안 가실 수 있는데 다시 설명을 하자면 for문의 i와 j의 표현을 잘 보셔야 합니다.
Lotto[i]은 현재 무작위 숫자를 추출하여 저장합니다.
for(j=0;j<i;j++){ }
위 for문은 j가 0 부터 j<i보다 작을 때까지 j가 1씩 증가합니다. 이표현은 j은 0~(i-1)까지의 반복한다는 의미입니다.
그러니깐 현재 i가 3이면 for문 j은 0~2까지 반복한다는 의미입니다.
즉, Lotto[2]이라 변수에 새로운 랜덤숫자가 저장되고 for문 j에서 0~1까지 Lotto[0], Lotto[1]을 각각 Lotto[2]와 비교하여 중복이면 i값을 -1감소 시켜서 이전 상태로 되돌아가게 하여 다시 Lotto[2]변수에 새로운 랜덤숫자가 저장됩니다.
if(Lotto[i]==Lotto[j]){
i--;
break;
}
보시면 for문안에 if문으로 비교되는데 중복이 발생하면 i가 -1감소 시키고 break문으로 해서 for문을 빠져나오게 됩니다. 중복이 발생하면 더이상 비교 할 필요가 없으니 루프문을 바로 빠져나오게 하는게 맞겠죠.
이렇게 해서 6개의 랜덤 숫자를 만들어 낼 수 있게 되었네요.
이제 코딩을 완성하고 정말 6개의 랜덤 숫자가 만들어지는지 실행을 시켜봐야겠죠.
2. 코딩
[소스]
#include <stdio.h>
#include <time.h>
int main(int argc, char *argv[]) {
int i,j;
int Lotto[6];
srand(time(NULL)); //랜덤초기값 초기화
for(i=0;i<6;i++){
Lotto[i]=(rand()%45)+1; //무작위 숫자 추출
for(j=0;j<i;j++){
if(Lotto[i]==Lotto[j]){ //중복 체크
i--;
break;
}
}
}
for(i=0;i<6;i++){
printf("%d ",Lotto[i]); //출력
}
return 0;
}
[결과]

정상적으로 무자위 숫자 6개가 만들어 졌네요.
마무리
오늘은 지금까지 배운 내용을 토대로 코딩 실습을 해보았습니다. 간단히 기본 개념만 계속 넘어가면 이런게 과연 어디서 써먹고 뭘 만들 수 있지하고 고민 하실 수 있습니다. 이렇게 배우고 나서 뭘 만들 수나 있을지 하고 생각하실 수 있습니다. 지금까지 배운 내용을 토대로 간단히 랜덤 로또 번호 생성기를 만들어 보았습니다. 이처럼 조금한 상상하면 재밌는 것들을 어렵지 않게 만들 수 있습니다. 단 각 개념을 최소한의 동작 원리를 이해했다는 조건하에서이지만요.
그리고 이 코딩은 아직 불안전한 코딩입니다. 그 이유가 뭘까요. 바로 숫자들이 무작위로 6개가 추출하여 저장되지만 출력 된 결과를 보시면 작은수와 큰수가 정렬이 되어 있지 않습니다. 즉, 정렬알고리즘이 빠져 있는 코딩이지요. 이건 여러분들이 정렬알고리즘을 찾아서 한번 추가해 보세요. 정렬알고리즘으로 순차, 버블, 삽입, 선택, 퀵, 합병, 쉘 정렬 등이 있는데 아무거나 구글검색을 통해 알고리즘을 찾아서 한번 수정해 보세요. 간단히 2 중 for문을 이용해서 위의 중복제거 코딩문과 유사하게 순차적으로 비교하여 정렬 코딩을 할 수 있습니다. 위 코딩을 응용하여 직접 코딩해보셔도 됩니다. 위 코딩을 응용 할 것인지 아니면 정석으로 정의된 외부 정렬알고리즘을 찾아서 그냥 적용 할 것인지는 여러분의 몫입니다.

for문이 개념만 잘 잡고 이해하면 정말 최고로 쓸모가 많은 부분인것 같아요 ㅎㅎ
그쵸! 여러 데이터를 건들 때에는 꼭 for문을 써야하기 때문에 제대로 알아두면 써먹을 곳이 참 많죠.