본문 바로가기

Exercise & Quizz/C

빙고 게임 - 연속되는 숫자 찾기

문제 : 0~9까지의 정수가 10x10 으로 랜덤하게 배열되어 있다. 가로, 세로, 대각선으로 연속되는 숫자의 갯수를 찾아서, 가장 많이 연속되는 숫자를 출력하라.

 

  흔히 "빙고" 게임으로 불리는, 랜덤하게 배열된 숫자에서 연속된 숫자를 체크하는 문제이다. 가로, 세로 외에 대각선이 두 방향이 있다는 점을 주의할 것. 


  c의 이중배열은 배열은 실제로 손으로 숫자를 나열한 경우와 x, y 좌표가 반대이다. 이 부분은 직접 손으로 해보고 신중하게 검토해 볼 것. 아주 잘 헛갈리는 문제이다. 


#include <stdio.h>
#include <stdlib.h>
#include <time.h>

#define MAX_NUMBER 10
#define SIZE 10
int test[SIZE][SIZE];
int answerList[MAX_NUMBER];

int getAnswer(int game[SIZE][SIZE], int maxNumber);
int checkTopDown(int game[SIZE][SIZE], int px, int py, int maxNumber);
int checkLeftRight(int game[SIZE][SIZE], int px, int py, int maxNumber);
int checkLeftTopRightDown(int game[SIZE][SIZE], int px, int py, int maxNumber);
int checkRightTopLeftDown(int game[SIZE][SIZE], int px, int py, int maxNumber);

int main(void) 
{
	int i,j;

	/* Init game */
	srand ( time(NULL) );

	for (i = 0; i < SIZE; i++)
	{
		for (j = 0; j < SIZE; j++)
		{
			test[i][j] = rand() % MAX_NUMBER;
		}
	}

	/* print test */
	for (i = 0; i < SIZE; i++)
	{
		for (j = 0; j < SIZE; j++)
		{
			printf("%d", test[i][j]);
		}
		printf("\n");
	}
	printf("\n");
				
	/* init answerList */
	for (i = 0; i< MAX_NUMBER; i++)
	{
		answerList[i] = 0;
	}

	printf ("Longest Number is %d.", getAnswer(test,MAX_NUMBER));

	return 0;	
}

int getAnswer(int game[SIZE][SIZE], int maxNumber)
{
	int i, j;
	int biggestNumber = -1;
	int longestArray = -1;

	for (i = 0; i < SIZE; i++)
	{
		for (j = 0; j < SIZE; j++)
		{
			checkTopDown(game, i, j, maxNumber);
			checkLeftRight(game, i, j, maxNumber);
			checkLeftTopRightDown(game, i, j, maxNumber);
			checkRightTopLeftDown(game, i, j, maxNumber);
		}
	}

	/* Return biggest number */
	for (i = 0; i < MAX_NUMBER; i++)
	{
		if (longestArray <= answerList[i])
		{
			biggestNumber = i;
			longestArray = answerList[i];
		}
	}

	return biggestNumber;
}

int checkTopDown(int game[SIZE][SIZE], int px, int py, int maxNumber)
{
	int i;
	int result = 1;

	if ((py -1 >= 0) &&  (game[py][px] == game[py-1][px]))
		return 0;

	for (i = py; i < SIZE - 1; i++) 
	{
		if (game[i][px] == game[i+1][px])
		{
			result++;
		}
		else
		{
			break;
		}
	}

	if (answerList[game[py][px]] < result)
	{
		answerList[game[py][px]] = result;
	}

	return result;
}

int checkLeftRight(int game[SIZE][SIZE], int px, int py, int maxNumber)
{
	int i;
	int result = 1;

	if ((px -1 >= 0) && (game[py][px] == game[py][px-1]))
		return 0;

	for (i = px; i < SIZE - 1; i++) 
	{
		if (game[py][i] == game[py][i+1])
		{
			result++;
		}
		else
		{
			break;
		}
	}

	if (answerList[game[py][px]] < result)
	{
		answerList[game[py][px]] = result;
	}

	return result;
}

int checkLeftTopRightDown(int game[SIZE][SIZE], int px, int py, int maxNumber)
{
	int i;
	int j = 0;
	int result = 1;

	if ((px -1 >= 0) && (py -1 >= 0) && (game[py][px] == game[py-1][px-1]))
		return 0;

	for (i = px; i < SIZE - 1; i++) 
	{
		if (game[py+j][px+j] == game[py+j+1][px+j+1])
		{
			result++;
			j++;
		}
		else
		{
			break;
		}
	}

	if (answerList[game[py][px]] < result)
	{
		answerList[game[py][px]] = result;
	}

	return result;
}

int checkRightTopLeftDown(int game[SIZE][SIZE], int px, int py, int maxNumber)
{
	int i;
	int j = 0;
	int result = 1;

	if ((px + 1 < SIZE-1) && (py -1 >= 0) && (game[py][px] == game[py-1][px+1]))
		return 0;

	for (i = px; i < SIZE ; i++) 
	{
		if (px - i < 0)
		{
			break;
		}
		else if ((px-j-1 > 0) && (py+j+1 < SIZE) && (game[py+j][px-j] == game[py+j+1][px-j-1]))
		{
			result++;
			j++;
		}
		else
		{
			break;
		}
	}

	if (answerList[game[py][px]] < result)
	{
		answerList[game[py][px]] = result;
	}

	return result;
}

#define을 이용하여 사이즈와 숫자 범위를 조정할 수 있도록 했고, 랜덤하게 만들어진 문제를 출력해서 쉽게 비교해볼 수 있도록 했다. 다시 말하지만, x, y 좌표과 실제로 출력되는 x, y는 x,y 순서쌍이 바뀌어 있음을 유의할 것.


'Exercise & Quizz > C' 카테고리의 다른 글

사전 순으로 단어 정렬하기  (0) 2014.07.19