블랙잭
기획
블랙잭은 플레이어가 갖고있는 카드 점수의 합입 21을 넘지 않는 한도 내에서, 타 사용자와 겨루어 점수가 높으면 이기는 게임이다.
블랙잭에서 카드는 스페이드, 하트, 클럽, 다이아몬드 4가지 무늬가 있다.
무늬별로 A, 2, 3, 4, 5, 6, 7, 8, 9, 10, J, Q, K의 13가지 카드 숫자가 존재한다.
(카드는 52장으로 구성된다.)
카드 배점
A 카드는 1점 또는 11점 중 유리한 대로 선택할 수 있다.
J, Q, K카드는 10점이다.
블랙잭 게임 동작
손님의 이름을 입력받는다.
카드 1벌(52장)을 잘 섞어서 사용한다.
다 쓰면 1벌을 "새로" 만들어 다시 잘 섞어서 사용한다.
처음에 카드는 처음 2장씩 나누어준다. (게임 기본값)
(카드 배분 순서는 손님 -> 딜러 -> 손님 -> 딜러)
* 딜러의 첫 카드는 보여주지 않고, 두번 째로 받은 카드만을 보여준다.
손님은 점수가 21점 미만인 경우 카드를 "원하는 만큼" 추가요청한다.
(종료할 수도 있고, 더 받을수도 있다.)
손님에게 추가카드를 원하는 지 요청을 받는다
(요청은 Y or N)
딜러는 카드의 합이 16점이하이면, 한장받는다.
17점 이상이면 안받는다. (딜러의 규칙)
A카드는 1 or 11 유리한 쪽으로 선택한다.
(처음에 11로 받아두고, 21을 초과하면 10을 빼서 유리한 카드 덱을 만든다.)
손님은 이길 때마다 칩을 하나씩 획득한다.
첫 두장의 합이 21이 되면 이 경우 칩을 두개 획득한다.
손님이 지면 칩을 하나 잃는다.
손님과 딜러가 비길 경우 칩의 변동이 없다.
손님이 보유하고 있는 칩의 개수는 매 라운드가 진행하면서 항상 보여준다.
잃은 경우 음수가 될 수도 있다.
프로그램의 역할
게임 운영진 : 딜러
게임 플레이어 : 유저
게임 플레이어 상대 : 딜러
게임에 사용될 물체 : 카드 덱, 카드
설계 - MVC 아키텍처
코드 구현
Card 클래스 - 카드 정보 Data Model 클래스
// Card 정보 Data 생성
public class Card {
public static final String SPADES = "spades";
public static final String HEARTS = "hearts";
public static final String DIAMONDS = "diamonds";
public static final String CLUBS = "clubs";
public static final int ACE = 1;
public static final int JACK = 11;
public static final int QUEEN = 12;
public static final int KING = 13;
public static final int SIZE_OF_ONE_SUIT = 13;
private String suit;
private int rank;
// Card 생성 메소드
/*
* 카드의 무늬 & 숫자를 지정
*/
public Card(String s, int r) {
suit = s;
rank = r;
}
// 카드의 무늬
public String suit() {
return suit;
}
// 카드의 숫자
public int rank() {
return rank;
}
// 카드가 동일한 카드인지 비교
public boolean equals(Card c) {
return suit.equals(c.suit()) && rank == c.rank();
}
}
CardDeck 클래스 - 카드 덱 Data 생성 Model 클래스
// 카드 덱 Data를 생성하는 Model 클래스
public class CardDeck {
private int card_count; // 남은 카드 수
private Card[] deck = new Card[4 * Card.SIZE_OF_ONE_SUIT];
// Invariant: deck[0], .., decl[card_count-1] 에 카드가 있다.
// 생성 메소드
public CardDeck() {
createDeck();
}
// 카드 덱 Data 생성
/*
* 53장 생성
*/
private void createDeck() {
createSuit(Card.SPADES);
createSuit(Card.HEARTS);
createSuit(Card.CLUBS);
createSuit(Card.DIAMONDS);
}
/*
* 무늬별로 13장 카드 생성
*/
private void createSuit(String which_suit) {
for(int i = 1; i <= Card.SIZE_OF_ONE_SUIT; i++) {
deck[card_count] = new Card(which_suit, i);
card_count = card_count + 1;
}
}
/*
* 카드 덱에서 카드를 하나 뽑아줌.
* 게임진행하며 카드 덱 관리할 때 사용
*/
/** newCard - 임의의 새 카드 한 장을 뽑아 줌
* @return 카드 덱에서 임의로 한 장을 뽑아 리턴
* 없으면 카드 1벌을 새로 만들고 한 장을 뽑아 리턴 */
public Card newCard() {
if (! this.moreCards())
createDeck();
int index = (int)(Math.random() * card_count);
Card card_to_deal = deck[index];
// for문 제어식이 int i = index; i < card_count
// deck[i] = deck[i+1];
for (int i = index+1; i < card_count; i++)
deck[i-1] = deck[i];
card_count = card_count - 1;
return card_to_deal;
}
/*
* 카드 덱에 카드가 남아있는지를 확인해주는 체크 메소드
*/
/** moreCards - 카드 덱에 카드가 남아있는지 알려줌
* @return 있으면 true, 없으면 false */
public boolean moreCards() {
return card_count > 0;
// return card_count >= 0;
}
}
CardPlayerBehavior 인터페이스 - 종속적인 관계를 독립적으로 분리하기 위한 도구
public interface CardPlayerBehavior {
/** wantsACard - 카드 한 장을 받겠는지 답한다.
* @return 카드를 받고 싶으면 true, 아니면 false */
public boolean wantsACard();
/** receiveCard - 카드를 한장 받는다. 한도(배열 hand의 크기)를 초과하면 받을 수 없다.
* @param c - 카드
* @return 성공적으로 받았으면 true, 그렇지 않으면 false */
public boolean receiveCard(Card c);
}
CardPlayer 클래스 - 카드 덱 Data 관리 Model 클래스
{유저-컴퓨터 클래스의 부모 클래스}
// 블랙잭 (유저 - 컴퓨터)의 카드 덱 클래스 (생성, 관리)
// 해당 클래스는 매 판마다 초기화를 진행해주는 가?
// 컴퓨터, 유저 모델 클래스를 초기화해주는 건가? 아니면, 부모 클래스인 CardPlayer 클래스만 초기화해주는 건가?
public abstract class CardPlayer implements CardPlayerBehavior {
private Card[] hand; // 갖고 있는 카드
private int card_count; // 갖고 있는 카드의 장 수
// 유저 - 컴퓨터의 카드 덱을 초기화해주기위해 hand가 가지는 수 저장.
private int maxCards;
// 생성 메소드
/** Constructor CardPlayer - max_cards 카드를 수용가능한 Card 배열 객체를 만들어 CardPlayer 생성
* @param max_cards - 들고 있을 수 있는 카드의 최대 장수 */
public CardPlayer(int max_cards) {
// Card 타입으로 배열객체 생성 - 생성 인자 할당 x -> 초기화 안됨.
maxCards = max_cards;
hand = new Card[max_cards];
card_count = 0;
}
// abstract 메소드
/** wantsACard - 카드 한 장을 받겠는지 답한다.
* @return 카드를 받고 싶으면 true, 아니면 false */
public abstract boolean wantsACard();
// (유저 - 컴퓨터)의 카드 덱에 카드 한장을 추가하는 메소드
/** receiveCard - 카드를 한장 받는다. 한도(배열 hand의 크기)를 초과하면 받을 수 없다.
* @param c - 카드
* @return 성공적으로 받았으면 true, 그렇지 않으면 false */
public boolean receiveCard(Card c) {
if (card_count < hand.length) {
hand[card_count] = c;
card_count += 1;
return true;
}
else
return false;
}
// (유저 - 컴퓨터)의 카드 덱을 보여주는 메소드
/** showCards - 들고 있는 카드를 내준다.
* @return 들고 있는 카드 전체 */
public Card[] showCards() {
Card[] card = new Card[card_count];
for (int i = 0; i < card_count; i++)
card[i] = hand[i];
return card;
}
// 블랙잭 게임진행 점수 생성 메소드
public int totalScore() {
int total_score = 0;
for(int i = 0; i < card_count; i++ ) {
int rank = hand[i].rank();
// ACE 무늬카드가 나왔을 때 예외처리 { 유리한 방향으로 카드 선택 }
if(rank == 1) {
if(total_score + 11 > 21 ) {
total_score = total_score + 1;
}
else {
total_score = total_score + 11;
}
// J,Q,K 무늬카드가 나왔을 때 예외처리
}
else if(rank == 11 || rank == 12 || rank == 13) {
total_score = total_score + 10;
}
else {
total_score = total_score + rank;
}
}
return total_score;
}
// 매 판이 종료되고 이어서 게임을 진행할 때, 유저 - 컴퓨터 카드 덱 초기화
public void resetHand() {
hand = new Card[maxCards];
card_count = 0;
}
}
HumanPlayer 클래스 - 유저의 카드 덱 Data 관리 Model 클래스
{CardPlayer 클래스 상속}
import javax.swing.*;
public class HumanPlayer extends CardPlayer {
// 유저 정보
public String name;
private int chips;
// 생성 메소드
public HumanPlayer(int max_cards, String n) {
// CardPlayer 클래스 상속받음.
/*
* 유저의 카드 덱 생성
*/
super(max_cards);
name = n;
}
// CardPlayer 클래스에서 상속받아 사용하는 abstract 메소드
public boolean wantsACard() {
String response = JOptionPane.showInputDialog("한장 더 드릴까요? (Y/N)");
return response.equals("Y");
}
// TO DO youWin(), youWinBlackjack(), youLose(), youDraw(), chips()
public void youWin() {
chips = chips + 1;
System.out.println("You Win!");
}
public void youWinBlackjack() {
chips = chips + 2;
System.out.println("You Win! Blackjack ~ !");
}
public void youLose() {
chips = chips - 1;
System.out.println("You Lose..");
}
public void youDraw() {
chips = chips;
System.out.println("Draw!!!");
}
// 유저 칩 갯수 리턴
public int chips() {
return chips;
}
}
ComputerPlayer 클래스 - 컴퓨터의 카드 덱 Data 관리 Model 클래스
{CardPlayer 클래스 상속}
import javax.swing.JOptionPane;
public class ComputerPlayer extends CardPlayer {
int maxCards;
// 생성 메소드
public ComputerPlayer(int max_cards) {
// CardPlayer 클래스 상속받음.
/*
* 컴퓨터 카드 덱 생성
*/
super(max_cards);
}
// abstract 메소드인 wantsACard() 구현
public boolean wantsACard() {
// 컴퓨터의 카드 덱 받기 & 안받기 의사결정
boolean decision;
Card[] cards = showCards();
// 게임에 따라 다른 전략을 세움
if(totalScore() <= 16) {
decision = true;
}
else {
decision = false;
}
return decision;
}
}
Dealer 클래스 - 카드 덱 Data를 받아서 블랙잭 유저들에게 카드를 뿌려주는 Model 클래스
// 블랙잭 게임의 카드 덱을 관리하는 Model 클래스
// 컴퓨터 - 유저한테 카드 뿌려줌.
public class Dealer {
CardDeck deck;
// 생성 메소드
public Dealer() {
deck = new CardDeck();
}
// 카드를 원할 때까지 주는 메소드
/*
* 카드 2장을 모두 나눠준 뒤의 실행될 카드 뿌리기 메소드
*/
public void dealTo(CardPlayerBehavior p) {
while (p.wantsACard()) {
p.receiveCard(deck.newCard());
}
}
// 카드를 한번만 주는 메소드
/*
* 처음 카드 2장을 나눠줄 때 사용할 카드 뿌리기 메소드
*/
public void dealOneTo(CardPlayerBehavior p) {
p.receiveCard(deck.newCard());
}
}
BlackJackController 클래스 - 블랙잭 게임을 컨트롤하는 Controller 클래스
import javax.swing.JOptionPane;
public class BlackJackController {
private Dealer dealer;
private HumanPlayer hand_player;
private ComputerPlayer hand_dealer;
// Controller의 생성 메소드
public BlackJackController(Dealer d) {
dealer = d;
}
// Controller의 메소드
public void manageBlackjack() {
boolean game_status = true;
// 유저 - 컴퓨터의 카드 덱 저장 - 출력
Card[] card_player;
Card[] card_dealer;
String name = JOptionPane.showInputDialog("플레이어의 이름을 입력하세요");
System.out.println("플레이어 이름: "+ name);
// 플레이어 객체 생성
hand_player = new HumanPlayer(53, name);
// 컴퓨터 플레이어 객체 생성
hand_dealer = new ComputerPlayer(53);
System.out.println("Your Chips: "+ hand_player.chips() + "\n");
while(game_status) {
System.out.println("+----------+----------------+-------------+\n\n");
// 게임 처음,
/*
* 카드를 두장씩 유저, 컴퓨터에게 뿌림.
*/
dealer.dealOneTo(hand_player);
dealer.dealOneTo(hand_dealer);
dealer.dealOneTo(hand_player);
dealer.dealOneTo(hand_dealer);
// 카드 2장 나눠주고, 유저 - 컴퓨터 카드덱 출력
card_player = hand_player.showCards();
card_dealer = hand_dealer.showCards();
System.out.println("Player Card");
for(int i = 0; i < card_player.length; i++) {
System.out.print(card_player[i].suit());
if(card_player[i].rank() == 1){
System.out.println(" ACE");
}
else if(card_player[i].rank() == 11) {
System.out.println(" JACK");
}
else if(card_player[i].rank() == 12) {
System.out.println(" QUEEN");
}
else if(card_player[i].rank() == 13) {
System.out.println(" KING");
}
else {
System.out.println(" "+card_player[i].rank());
}
}
System.out.println(hand_player.totalScore()+ "\n");
System.out.println("Dealer Card");
for(int i = 1; i < card_dealer.length; i++) {
System.out.print(card_dealer[i].suit());
if(card_dealer[i].rank() == 1){
System.out.println(" ACE");
}
else if(card_dealer[i].rank() == 11) {
System.out.println(" JACK");
}
else if(card_dealer[i].rank() == 12) {
System.out.println(" QUEEN");
}
else if(card_dealer[i].rank() == 13) {
System.out.println(" KING");
}
else {
System.out.println(" "+card_dealer[i].rank());
}
}
// System.out.println(hand_dealer.totalScore()+ "\n");
System.out.println("\n");
// 게임 진행
if(hand_player.totalScore() == 21) {
hand_player.youWinBlackjack();
}
else {
while(hand_player.totalScore() < 21 && hand_player.wantsACard()) {
dealer.dealOneTo(hand_player);
// 플레이어 카드 덱 출력
card_player = hand_player.showCards();
System.out.println("Player Card");
for(int i = 0; i < card_player.length; i++) {
System.out.print(card_player[i].suit());
if(card_player[i].rank() == 1){
System.out.println(" ACE");
}
else if(card_player[i].rank() == 11) {
System.out.println(" JACK");
}
else if(card_player[i].rank() == 12) {
System.out.println(" QUEEN");
}
else if(card_player[i].rank() == 13) {
System.out.println(" KING");
}
else {
System.out.println(" "+card_player[i].rank());
}
}
System.out.println(hand_player.totalScore()+ "\n");
}
if(hand_player.totalScore() > 21) {
hand_player.youLose();
}
else if(hand_player.totalScore() == 21) {
hand_player.youWinBlackjack();
}
// 유저 턴 종료 - 21이하인 채로 종료
else {
while(hand_dealer.wantsACard() && hand_dealer.totalScore() < 21) {
dealer.dealOneTo(hand_dealer);
// 컴퓨터 카드 덱 출력
card_dealer = hand_dealer.showCards();
System.out.println("Dealer Card");
for(int i = 1; i < card_dealer.length; i++) {
System.out.print(card_dealer[i].suit());
if(card_dealer[i].rank() == 1){
System.out.println(" ACE");
}
else if(card_dealer[i].rank() == 11) {
System.out.println(" JACK");
}
else if(card_dealer[i].rank() == 12) {
System.out.println(" QUEEN");
}
else if(card_dealer[i].rank() == 13) {
System.out.println(" KING");
}
else {
System.out.println(" "+card_dealer[i].rank());
}
}
// System.out.println(hand_dealer.totalScore()+ "\n");
System.out.println("\n");
}
if (hand_dealer.totalScore() > 21) {
hand_player.youWin();
}
else if(hand_dealer.totalScore() == hand_player.totalScore()) {
hand_player.youDraw();
}
else if(hand_dealer.totalScore() < hand_player.totalScore()) {
hand_player.youWin();
}
// 컴퓨터가 블랙잭 or 컴퓨터의 카드 덱 total이 더 클 때
else {
hand_player.youLose();
}
}
}
// 한 턴 게임종료
/*
* 매 판마다 게임 종료 시
* 유저 - 컴퓨터 카드 덱 초기화 - 다음 게임을 진행
*/
hand_player.resetHand();
hand_dealer.resetHand();
System.out.println("Your chips: " + hand_player.chips() + "\n");
System.out.println("+----------+----------------+-------------+\n\n\n\n\n");
String continue_game = JOptionPane.showInputDialog("\n\n게임을 더 하시겠습니까?");
if(!continue_game.equals("y")) {
game_status = false;
}
}
System.out.println("Bye!!!!!");
}
}
BlackJack 클래스 - 블랙잭 Java Application의 Starter 클래스
public class BlackJack {
public static void main(String[] args) {
new BlackJackController(new Dealer()).manageBlackjack();;
}
}
새롭게 알게된 점 & 깨달은 점
상속을 사용하여 활용하는 방법에 대해 터득했다.
부모 클래스 정의대상에 대해서 알게 되었다.
아직까지는 스스로, 부모 클래스를 지정해서 상속받아 활용하는 방법은 모르겠지만, 상속받아서 자식클래스의 객체가 어떻게 활용되는지를 알게 되었다.
상속은 고유한 객체에게 고유한 역할을 추가하는 개발 전략
상속은 코드 재활용을 높인다는 이점도 있지만, 핵심은 상속을 통한 고유한 객체의 의미를 부여한다는 점이 가장 큰 핵심이다.
상속을 통해 자식클래스의 고유한 객체의 의미를 부여하게 된다.
이 점은 이번 과제에서 작성한 Java 코드를 리뷰해보면서 정리하도록 하겠다.
인터페이스를 선언 후 implement를 해서 독립적인 개발전략에 대해서 새롭게 알게되었다.
독립적인 개발이 가능했고, 구현이 완료되지않아도, 컴파일러를 통과하는 이점이 있었다.
그래서, 인터페이스에서 선언한 메소드에 대해서 CardPlayer 클래스에서 카드 받는 메소드인
receive()를 오버라이딩하여 해당 메소드를 작동할 수 있도록 작업을 하였다.
사실, 혼자서 개발을 했던 터라, 인터페이스의 이점을 제대로 누리지 못했다.
고유한 객체로써 Java 프로그램을 통제한다.
Model 클래스를 여러 개 분할해서 생성하는 이유를 이번 블랙잭을 통해서 알게되었다.
굳이, Model을 여러 개로 만드는 이유는 현실 세계에 빗대어 보면서 이해할 수 있다. 사람이 많은 식당에서 직원들을 역할에 맞추어 고용하는 원리와 똑같다.
Java도 프로그램을 구성하기 위해 고유한 Model 클래스를 생성하여 프로그램의 부품들을 클래스로 지정해두고, 고유하게 부여된 역할대로 객체를 생성하고, 이에 대한 원리로 Java 코드를 작성해 프로그램을 완성시킨다.
정리해서, 객체 지향 프로그래밍 개발전략은 고유한 역할을 지정해주고, (MVC 아키텍처 설계)
이에 따라 코드를 작성하면서 프로그램을 완성시킨다.
(고유한 역할을 지정해주는 MVC 아키텍처 설계에는 완벽한 답이 없고, 좋은 설계 중 하나를 택해서 설계를 완성시킨다.)
설게에는 정답이 없고, 좋은 방법 중 택하여 설계를 진행한다는 사실만 알면된다.
설계된 코드를 보고, 유지보수하려면
우선, 설계 방식에 대해 이해하고, 설계된 고유한 클래스들이 어떠한 고유한 역할을 부여받고 있는지를 이해하자.
(현재 프설방 실습들은 각기 다른 설계 방식으로 프로그램을 구성하고 있다.
비즈니스 소통력을 늘이면서, 이해도를 증가시키지만, 그 만큼 어렵고 힘들다.
그치만, 설계된 방식을 차근차근 이해하면서 고유한 클래스들의 역할이 무엇인지 깨닫는다면, 새로운 아키텍처로 코드를 구현해두어도 금방 적응해서 코드를 작성해날 수 있다.)
자식클래스에서 상속을 위한 메소드, super()
super() 메소드는 오직, 생성메소드에서만 실현된다.
과제하면서, 어려웠던 점
블랙잭 과제 중 겪은 객체 다루기 - 상황정리
이는, 블랙잭 과제 중 매 판이 끝나고, 이어서 게임을 진행할 때,
유저와 컴퓨터의 카드 덱 객체인 CardPlayer 클래스를 초기화하여
게임 셋팅을 다시 초기화해줬어야 되었다.
그래서, 객체 지향 원리에 따라 객체를 다루는 아이디어를 생각하였고, 이에따라
유저, 컴퓨터의 카드 덱은 Computer, Human 클래스에서 CardPlayer라는 클래스를 상속받아 관리되어진다.
그래서, 나는 매 판이 끝나고 이어서 다음 게임을 진행하려면, Computer, Human 클래스를 초기화해줘야되지 않을까 라는 생각을 했다.
되게 풀어쓸 게 많아서 객체 지향 프로그래밍 원리에 따라 생각해낸 아이디어를 하나씩 나열하도록 하겠다.
아래는 유저와 컴퓨터의 매 판마다의 카드 덱을 초기화해주기위해 시도한 방법들이다.
마지막 방법으로 해결했다.
Controller 클래스에서 HumanPlayer, ComputerPlayer 클래스 초기화
이렇게하면, 사실상 되기는 한다.
그치만, HumanPlayer, ComputerPlayer 클래스에서는 Chips와 User Name을 관리한다.
따라서, 아키텍처 설계상 Model 클래스로써 작동되어지기에,
해당 클래스를 일회성으로 사용하기 보다는, Model 클래스를 고유한 객체로
하나의 유저의 게임이 진행되는 동안 계속 가지고가도록 설계했다.
정리해서, MVC 아키텍처의 본질인 고유한 객체로써 작업을 분할해서 코드 작성 및 관리를 유용하게 만들어주는데,
내가 Controller 클래스에서 Model 클래스를 매 판마다 초기화를 해주면, MVC 아키텍처의 의미가 사라진다.
도교수님의 말씀대로,
MVC 아키텍처의 각각의 클래스들은 현실의 고유한 물체와 대응된다.
식당을 예로들면, 음식을 조리하는 요리사, 서빙을하는 서버, 결제를 담당하는 결제원으로 분할해서 식당을 운영하듯이
Java에서 코드를 작성할 때 MVC 아키텍처를 토대로 설계를해서 프로그램의 고유한 역할을 부여해준다.
이 역할은 객체로써 정의되고, 활용되어진다.
그래서, 이러한 의미가 누락되지않도록 MVC 아키텍처를 설계하고 이에 따라 코드를 작성하면,
JAVA를 활용한 객체 지향 프로그래밍을 수행할 수 있게된다.
이번 과제를 하면서, 객체의 의미에 대해서 많은 걸 깨닫게 해준 뜻깊은 경험이었다.
Java 과제를 마무리하면서 객체의 의미를 더 깊이있게 다뤄볼 것이다.
HumanPlayer, Computer 클래스에서 상속받고 있는 CardPlayer 클래스 초기화
With. super()
원하는 전략은 매 판이 끝나고, 유저와 컴퓨터가 지니고 있는 카드 덱을 초기화해주는 거였다.
매 판이 끝이나고, 블랙잭 게임을 다시 시작하기 위해 카드 덱을 초기화해줬다.
CardPlayer 클래스가 유저 - 컴퓨터의 카드 덱을 관리해주기에, 유저-컴퓨터 클래스에서 상속받아서 super()를 통해 초기화해줄 때, CardPlayer 클래스를 추가로 초기화해주는 메소드를 유저-컴퓨터 클래스의 메소드에 구현하려고 했다.
나의 논리상 완벽에 가까웠지만,,, 메소드를 추가 구현하여 super() 메소드를 사용하는 행위는 Java 언어에서 막고있었다.
super()메소드는 오직 클래스 생성메소드에서만 구현이 가능하다라고 Java에서 친절하게 알려줬다.
정리해서, 부모 클래스를 상속받아서 사용하고 있는 자식클래스에서
부모 클래스를 초기화해주는 super() 메소드는 자식 클래스의 생성 메소드에서만 구현이 가능하여 자식클래스에서 추가로 메소드를 구현하여 상속하고 있는 부모클래스를 초기화시킬 수 없다.
부모 클래스 전체를 초기화해주는 건, 부모 클래스에서 별도로 메소드로 구현해야됨을 알려주는 뜻깊은 경험이었다.
확실히 JAVA에서는 객체의 본질을 지키기위해 별도로 처리해둔 개발 규칙들이 많다는 걸
Java를 깊이있게 다뤄보면서 깨달아가고 있는 듯하다.
(해결)
상속받는 CardPlayer 클래스의 내부 메소드를 이용해 유저-컴퓨터 카드 덱 초기화
CardPlayer 클래스에 resetHand() 메소드를 추가구현하여 CardPlayer의 필드변수를 초기화하는 작업을 진행했다.
(매 판이 끝나고 이어서 새로운 게임을 진행할 때, 플레이어들의 카드 덱을 초기화하기 위해서 다음과 같은 작업을 수행했다.)
플레이어의 매 판마다 카드 덱을 저장하고 있는 클래스인 CardPlayer 클래스를 초기화시켜주었다.
HumanPlayer, ComputerPlayer 클래스는 CardPlayer 클래스를 상속받아서 유저, 플레이어의 카드 덱을 관리한다.
매 판마다 유저, 플레이어의 카드 덱을 초기화해주어야 하는데, CardPlayer를 자식 클래스에서 초기화시켜주는 방법이 존재하지 않아 CardPlayer 클래스 내부에서 카드 덱을 초기화해주는 메소드를 따로 만들어서 유저, 컴퓨터 카드 덱을 매판마다 초기화해주었다.
마무리..
이번과제는 객체 지향 프로그래밍 개발전략에 대해서 많이 생각해보게 해준 뜻깊은 과제였다.
혼자 힘으로 MVC 아키텍처 설게에 대해 이해하고, 이에 따라 코드를 작성했다.
그러면서, Model 클래스의 고유한 역할이 부여됨을 이해했고, 고유한 역할을 토대로 프로그램이 부품대로 구성되어 Java Application을 완성시킨다는 사실을 깨달았다.
요즘들어, 객체 지향 개발방법론에 대해서 깊이있게 생각하며 시야가 넓어지는 중이다.
객체 지향 프로그래밍은 Java를 2학기 때 처음접하면서 객체 지향에 대해서 신기함과 신비로움을 많이 느끼고 있는데, 이 점이 이젠 내게
추상적인 존재가 아닌, 의식적인 존재로 되어가고 있는 듯하다.
좀 더 노력해서 Java와 같은 객체 지향 프로그래밍 개발전략을 더 탄탄하게 만들어 볼 것이다.
객체 지향 프로그래밍을 통해 원하는 프로그램을 설계하고 안정적으로 완성하는 그날까지
열심히 그리고 열심히
'CS 대학강의' 카테고리의 다른 글
[CS 1-2 | 프로그램 설계 방법론] 텍스트 및 파일처리 17주차 (0) | 2022.11.17 |
---|---|
[CS 1-2 | 오픈소스 SW 기초] 사물인터넷 7주차 (0) | 2022.11.17 |
[CS 1-2 | 시스템 프로그래밍 기초] 시스템 프로그래밍 기초 - #16 [문자열] (0) | 2022.11.15 |
[CS 1-2 | 시스템 프로그래밍 기초] 함수 포인터 실습 15주차 (0) | 2022.11.11 |
[CS 1-2 | 프로그램 설계 방법론] Java GUI로 슬라이드 퍼즐게임 제작 13주차 (0) | 2022.11.11 |