전체코드
#include <stdio.h>
#include <time.h>
#include <stdlib.h>
//전역변수 선언
int level; // 레벨
int arrayFish[6]; // 어항
int* cursor; // 어항 배열에 접근해야하니까 포인터 변수 사용.
//함수 선언
void initData(); // 게임 초기화
void printfFishes(); //어항 물 높이 출력 함수
void decreaseWater(long elapsedTime); //어항의 물을 증발(감소)시키는 함수 선언
int checkFishAlive(); //모든 물고기가 죽었는지 확인 함수
int main(void) {
long startTime = 0; // long은 int와 같이 정수를 담을 때 사용, 시간을 다룰 때 주로 long을 사용
int num; //사용자가 입력하는 어항 번호를 받을 변수
long totalElapsedTime = 0; // 총 경과시간;
long prevElapsedTime = 0; //직전에 물을 준 시간(물을 준 시간 간격) : 10초에 물을 주고 13초에 다시 물을 줬다면 그 사이 간격이 3초
initData();
startTime = clock(); // c에서 제공하는 clock() 함수, 프로그램 수행 시작 시점부터 현재까지 흐른 시간을 밀리초 단위로 반환
cursor = arrayFish; // 포인터 변수에 어항 배열의 시작 주소 넣기
while (1) { // 어항에 물 주기 무한 반복
printfFishes();
printf("몇 번 어항에 물을 줄까요(1~6)");
scanf_s("%d", &num); //어항 번호 받기
if (num < 1 || num > 6) {
printf("\\n\\n === 입력값이 잘못됐습니다 === \\n\\n"); // 1~6인 어항 번호만 받을 수 있으므로 아닐 경우 안내 메세지
continue; // 어항 번호를 입력 받는 부분으로 다시 돌아가기
}
//총 경과시간, 초 단위로 표시
totalElapsedTime = (clock() - startTime) / CLOCKS_PER_SEC;// 총 경과 시간, 초 단위로 표시: 밀리초 단위라서 CLOCKS_PER_SEC(나눈 값을 초단위로 보여줌)로 나눔.
printf("총 경과시간: %1d초\\n", totalElapsedTime); // 총 시간 결과
// 물을 준 시간 간격
prevElapsedTime = totalElapsedTime - prevElapsedTime; // 물을 준 시간 간격 : 총 경과시간 - 직전에 물을 준 시간
printf("최근 경과시간: %1d초\\n", prevElapsedTime); // 최근 경과 시간
decreaseWater(prevElapsedTime); // 어항 물 증발(감소) 함수 호출
//사용자가 입력한 번호의 어항에 물 주기
if (cursor[num - 1] <= 0) {
printf("%d번 어항의 물고기는 이미 죽었으므로 물을 주지 않습니다.\\n", num);
//조건1: 어항 물 높이가 0어서 물고기 죽음.
//포인터 변수 cursor로 접근하고 몇 번 어항인지는 num변수로 알 수 있음.
// 배열은 0부터 시작하니까 num - 1을 해서 실제 배열의 인덱스가 되게 함.
}
else if (cursor[num - 1] + 1 <= 100) {
printf("%d번 어항에 물을 줍니다.\\n\\n", num);
cursor[num - 1] += 1;
// 조건2: 물높이가 100을 넘을 때
//조건에 해당하면 현재 물높이에 1을 더함.
}
if (totalElapsedTime / 20 > level - 1) {//레벨업 확인(20초마다 한번씩 수행)
level++; //레벨업
printf("***축하합니다. %d레벨에서 %d레벨로 올랐습니다. ***\\n\\n", level - 1, level); // 기존 레벨을 출력할 땐level - 1을 해야함.
if (level == 5) {
printf("***\\n\\n 축하합니다. 최고 레벨을 달성했습니다. 게임을 종료합니다.\\n\\n");
exit(0);
//최고레벨 확인 후 게임 종료
}
}
//모든 물고기가 죽었는지 확인
if (checkFishAlive() == 0) { //함수 호출해서 물고기가 0인지 확인
printf("모든 물고기가 죽음 ㅠㅜㅜ");
exit(0);
}
else {
printf("물고기 아직 살아있음.1!");
}
prevElapsedTime = totalElapsedTime;
}
return 0;
}
void initData() {
level = 1;
for (int i = 0; i < 6; i++) {
arrayFish[i] = 100; // 어항의 물은 가득 차있으니까 초기값 100
}
}
void printfFishes() {
printf("%3d번 %3d번%3d번%3d번%3d번%3d번\\n", 1, 2, 3, 4, 5, 6);
for (int i = 0; i < 6; i++) {
printf(" %3d", arrayFish[i]); // 어항 배열을 돌면서 6개 어항 물높이 출력, 최대 3자리까지만 출력
}
printf("\\n\\n");
}
void decreaseWater(long elapsedTime) { // 어항 6개에서 물을 증발시키는 동일한 작업을 수행하니 for문으로 돌리기
for (int i = 0; i < 6; i++) {
arrayFish[i] -= (level * 3 * (int)elapsedTime);
// 어항 6개 물 높이는 arrayFish에 저장되어 있음. 여기서 - 증발한 물의 양을 하면 현재 어항 물높이가 됨.
// 증발하는 물의 양은 난이도 조절을 위해 3으로 정함.
// int형인 다른 값과 곱하기 위해 앞에 int를 붙여 정수형으로 형변환
// ex) 1레벨에서 직전에 물을 주고 10초가 지났다면 1(level) * 3 * 10(elapsedTime) = 30만큼 물높이가 줄어들음.
if (arrayFish[i] < 0) {
arrayFish[i] = 0;
// 물 높이가 0이 되면 더이상 줄어들지 x, 그래서 값이 0보다 작으면 arrayFish[i] 값을 0으로 저장하고 다음 어항으로 넘어감.
}
}
}
int checkFishAlive() {
for (int i = 0; i < 6; i++) {
if (arrayFish[i] > 0) {
return 1;
}
}
return 0;
// 6개어항 중 물높이가 0보다 높은 어항이 하나도 없으면 물고기는 모두 죽음.
// if문을 실행하지 못하고 for문이 바로 끝나므로 for 문 뒤에서 0 반환
}
서식 지정자의 형식 태그
- printfFishes() 함수에서 서식 지정자에 넣는 숫자 3은 서식지정자에 옵션을 추가할 수 있는 형식 태그의 하나 자릿수라고 보면 되는데 3을 넣으면 3자리를 지정함.
- 만약 출력할 값이 지정 너비보다 작으면 자릿수를 맞추기 위해 빈칸으로 채움.
형변환
- C언어에서는 원하는 연산 결과를 얻기 위해 정수를 실수로, 실수를 정수로 바꾸는 경우가 있는데, 이를 형변환이라고 함. 즉 어떤 자료형을 다른 자료형으로 바꾸는 것.
더보기
== 형식 == (바꿀 자료형)변수명/값
어항에 물주기 에서는 arrayFish[i] -= (level * 3 * (int)elapsedTime); 이 부분
'언어 > C' 카테고리의 다른 글
[코딩자율학습] 15일차 동물카드 뒤집기 프로젝트 (0) | 2024.03.24 |
---|---|
[코딩자율학습] 14일차 다차원 배열 (0) | 2024.03.21 |
[코딩자율학습] 12일차 포인터 (0) | 2024.03.19 |
[코딩자율학습] 11일차 프로젝트: 자라나라 머리머리 (0) | 2024.03.18 |
[코딩자율학습] 10일차 배열과 문자열 (0) | 2024.03.15 |