[TIL] 2020-11-26

5315 단어 TILJavaprojectJava

진행과정

오늘은 그저께 만들어 두었던 코드를 최대한 깔끔하게 다듬고 승리조건 알고리즘을 만드는 작업을 해보았다. 생각보다 원활하게 진행되어 다행이라는 생각과 한편으로 자바수업을 들었을 때 보다 실력이 상승된 것 같아 기분이 좋은 하루였다. 그 때 과제로 만들려고 했으면 진작에 포기했을듯..

오늘 한 일

	Player[] player = new Player[2];
	Board board = new Board();
	CheckWin checkwin = new CheckWin();
	public Main()
	{
		System.out.println("오목 게임을 시작합니다.");
		System.out.print("첫번째 플레이어(흑돌)의 이름을 입력하세요. >>> ");
		String name1 = sc.next();
		player[0] = new Player(name1,"●");
		System.out.print("두번째 플레이어(백돌)의 이름을 입력하세요. >>> ");
		String name2 = sc.next();
		player[1] = new Player(name2,"○");
	}

플레이어 객체에 이름을 입력받을 수 있게 고쳤다. 게임이 실행되는 메인 클래스에 Player객체를 배열로 2개 만들어 주었고 Main()생성자 안에 이름을 입력받고 각 이름에 맞게 객체를 생성시켜 주었다.

void startTurn()
	{
		for(int i=0;i<player.length;i++)
		{
			play(board, player[0], player[1]);
			System.out.println(player[i].getPlayerName()+ "님이  차례입니다.");
			System.out.println("x좌표 입력:");
			int x = sc.nextInt();
			System.out.println("y좌표 입력:");
			char y = sc.next().charAt(0);
			
			if(x > 18 || y > 's'){
				System.out.println("범위를 벗어났습니다. 다시 입력해주세요.");
				i--;
			}
			else if(board.board[x][y-97] !=  "."){
				System.out.println("이미 돌이 존재하는 좌표입니다. 다시 입력해주세요.");
				i--;
			}

확실히 객체를 배열로 만들고 나니 편리했다. 이전 코드는 턴을 돌아가게 하는 메소드 두개를 만들어 게임을 진행시켰는데 배열을 생성하고 for문을 사용하니 메소드 하나로만 돌아가게 만들었다. 훨씬 깔끔하고 코드가 줄어든 모습이다. 그리고 각 순서에 맞는 이름을 출력시키고 입력받은 xy의 좌표가 오목판 크기보다 크다면 에러메세지를 출력시켜주고 다시 둘 수 있게 만들어 주었다.


else{
	System.out.println();
	System.out.println(player[i].getPlayerName()+"님이 " +x+","+y+"에 수를 놓습니다.");
	board.put(x, y, player[i]);
	checkwin.board = board.board; //승패분석을 위해 오목판을 checkwin메소드에도 넣어줌
	if(checkwin.winOrnot1(x, y, player[i]) || checkwin.winOrnot2(x, y, player[i]) || checkwin.winOrnot3(x, y, player[i]) || checkwin.winOrnot4(x, y, player[i]) || checkwin.winOrnot5(x, y, player[i]) || checkwin.winOrnot6(x, y, player[i])) //승패분석
	{
		board.print();
		System.out.println(player[i].getPlayerName()+ "님이 승리하였습니다.");
		System.exit(0);
			}
		}
	}
}

이어서 startTurn()메소드의 부분인데 입력받은 좌표에 수를 놓는다는 출력문과 승리조건 메소드 checkwin()에 입력받은 좌표를 똑같이 넣었다. 이는 좌표값을 받아 승리조건을 따지기 위함이다. 그리고 승리조건을 충족시키면 오목판을 출력시키고 승리하였다는 출력문과 프로그램을 종료시킨다. if문 쪽이 매우 긴 것을 볼 수 있는데 메소드 이름을 줄이던가 해야할 것 같다.

void run()	
{
	while(true)
	{
		startTurn();
	}
}

턴이 돌아가는 메소드를 하나로 합쳤기 때문에 run()메소드도 함께 줄어든 모습이다.

class CheckWin extends Board{
	boolean winOrnot1(int x, char y, Player player) //오른쪽으로 가로 5개
	{
		try {
			if(board[x][y-97] == player.getPlayerStone() && board[x][y-98] == player.getPlayerStone() && board[x][y-99] == player.getPlayerStone() && board[x][y-100] == player.getPlayerStone() && board[x][y-101] == player.getPlayerStone())
			{
				return true;
			}
			else
				return false;
		}catch(ArrayIndexOutOfBoundsException e)
		{
			return false;
		}
	}

오늘의 가장 중요한 메소드 CheckWin()이다. 승리조건을 어떻게 구상해야 할까 곰곰히 생각을 해보았는데 그냥 플레이어가 두는 수 마다 조건을 따지는 것을 선택했다. boolean으로 y좌표를 97부터 101까지 같은 돌이면 true를 리턴 시켜 주었고 try catch문을 이용해 오목판 구석좌표에 돌을 두었을 때 -좌표가 들어갈 수 있으므로 예외처리를 시켜주었다.

처음 승리조건을 만들기 시작할 때 가로조건에서 메소드 하나만으로 모든 경우를 커버칠 줄 알았는데 왼쪽에서 오른쪽으로 5돌을 두는 경우, 오른쪽에서 왼쪽으로 5돌을 두는 경우, 가운데에서 5돌을 완성시키는 경우 등 5개의 메소드가 필요하다는 것을 알았다.
다시말하면 가로,세로,왼쪽 대각선, 오른쪽 대각선 각각 5개, 총 20개의 메소드가 필요하다는 말이다.

TIL

그저께 내가 목표하려던 turn메소드 정리하기와 승리조건 알고리즘 초입까지는 끝냈다. 하지만 코드가 돌아가게만 하기 위해 winOrnot메소드를 너무 지저분하게 만들지 않았나 라는 생각이 들어 내일 정리 할 예정이다. 다행이 끝이 보이는 것 같다. 목표는 일주일로 정했지만 시간이 조금 남을 수도 있을 것 같아 빨리 끝내게 된다면 GUI구현도 생각중에 있다.

좋은 웹페이지 즐겨찾기