質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

ただいまの
回答率

87.37%

三つそろった時の表示

解決済

回答 3

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 1,001
退会済みユーザー

退会済みユーザー

現在、プログラム作成してますが、三列そろったかと勝敗判定につまっています。
解説もつけていただけるとうれしいです。よろしくお願いします。

import java.io.*;
class Circle{
    public static void main(String args[])throws IOException{

    //〇×の盤
    int [][] chart=new int[3][3];

        while(true){
            while(true){

                //列行の数字入力(プレイヤー1)

                //列行の数字入力
                System.out.print("列番号入力");
                BufferedReader br = new BufferedReader( new InputStreamReader(System.in));

                String str=br.readLine();
                int input=Integer.parseInt(str);

                //行の数字入力
                System.out.print("行番号入力");

                String str2=br.readLine();
                int input2=Integer.parseInt(str2);


            //盤表示
            for(int x=0;x<chart.length;x++){
                    System.out.println(" ");
                for(int y=0;y<chart[x].length;y++){
                    System.out.print(chart[x][y]);
                }
            }

            //列行の数字入力
            while(true){

                //列行の数字入力(プレイヤー2)

                //列行の数字入力
                System.out.print("列番号入力");

                BufferedReader br = new BufferedReader( new InputStreamReader(System.in));

                String str3=br.readLine();
                int input3=Integer.parseInt(str3)-1;

                //行の数字入力
                System.out.print("行番号入力");

                String str4=br.readLine();
                int input4=Integer.parseInt(str4);


            //盤表示
            for(int x=0;x<chart.length;x++){
                    System.out.println(" ");
                for(int y=0;y<chart[x].length;y++){
                    System.out.print(chart[x][y]);
                }
            }
        }
    }
}    
  • 気になる質問をクリップする

    クリップした質問は、後からいつでもマイページで確認できます。

    またクリップした質問に回答があった際、通知やメールを受け取ることができます。

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

質問への追記・修正、ベストアンサー選択の依頼

  • aikon_marimo

    2019/02/08 23:23

    これだとそもそもプレイヤー1の//盤表示の箇所に処理がいかないのでは?
    それと、具体的には勝敗判定のどの部分が分からないでしょうか?文法的な話か、ロジック的な話かを記載いただけると助かります。

    キャンセル

  • 退会済みユーザー

    退会済みユーザー

    2019/02/08 23:31

    話→文法・ロジック両方だとありがたいです。
    〇を置く→(縦・横・ななめ)どこかそろったか見たいので。。

    キャンセル

回答 3

checkベストアンサー

0

工夫次第で簡単に記載もできますが、必要なチェックは下記のような簡単なものです。
#質問欄に記載頂いているくらいのソースが書けるなら、下図の2次元配列も理解できてそうなので、自力で出来そうな気がしますけどね。

下記はマルのチェックのみなので、バツのチェックを追加して毎ターン、このチェックを呼び出せば勝敗判定できます。

    chart        
    [0][0]    [0][1]    [0][2]
    [1][0]    [1][1]    [1][2]
    [2][0]    [2][1]    [2][2]

    ★横が揃ったかのチェック        
    if (chart[0][0] == 1 && chart[0][1] == 1 && chart[0][2] == 1 ) {        
        // 1行目に、1(マル)が揃ってる    
    }        
    else if (chart[1][0] == 1 && chart[1][1] == 1 && chart[1][2] == 1 ) {        
        // 2行目に、1(マル)が揃ってる    
    }        
    else if (chart[2][0] == 1 && chart[2][1] == 1 && chart[2][2] == 1 ) {        
        // 3行目に、1(マル)が揃ってる    
    }        
    ★縦が揃ったかのチェック        
    if (chart[0][0] == 1 && chart[1][0] == 1 && chart[2][0] == 1 ) {        
        // 1列目に、1(マル)が揃ってる    
    }        
    else if (chart[0][1] == 1 && chart[1][1] == 1 && chart[2][1] == 1 ) {        
        // 2列目に、1(マル)が揃ってる    
    }        
    else if (chart[0][2] == 1 && chart[1][2] == 1 && chart[2][2] == 1 ) {        
        // 3列目に、1(マル)が揃ってる    
    }        
    ★斜めが揃ったかのチェック        
    if (chart[0][0] == 1 && chart[1][1] == 1 && chart[2][2] == 1 ) {        
        // 斜め右下がりに、1(マル)が揃ってる    
    }        
    else if (chart[2][0] == 1 && chart[1][1] == 1 && chart[0][2] == 1 ) {        
        // 斜め右上がりに、1(マル)が揃ってる    
    }        

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2019/02/09 00:01

    ありがとうございます!

    キャンセル

  • 2019/02/09 21:56

    再度すいません。
    上記(〇チェック)のプログラムはどこに追加すればよいかご教授いただけますか。

    キャンセル

  • 2019/02/09 22:23

    質問に記載されたソースの最後(//盤表示の先or後)で良いと思います。
    追加方法についてはkatoyさんの回答が参考になるかと思います。

    キャンセル

0

全てを一度に作ろうとせず, 部分から作られては如何でしょうか.
大きく見て分からないことを分割して, 出来る細かさまで落とすこともプログラミングの技術です.
提示された main メソッドのように全てを並べると, どこが何をしていたのかも分からなくなることがあります.
分割して考えるとともにその分割をメソッドとして表現することで, 作るべき機能に集中して作業することも出来るようになります.

ご質問の機能も, コードが分かったからとこの main メソッドに直接埋め込むと, 例えコメントを書いても埋もれて目立たなくなります.
勝敗判定をメソッドとして設計することで, 他の変数などを気にせずに集中することが出来ます.

まずインターフェースを設計してみましょう.
勝敗判定に必要な盤は chart[0~2][0~2] で表現されています. 値は 0=空き, 1=プレイヤ1, 2=プレイヤ2です. これをパラメータで渡します.
戻りは勝ったプレイヤの番号(1 or 2) または勝敗が決まっていなければ 0 としましょう.
名前は…テキトウに judgment とします.
すると,

/**
 * 勝敗を判定します.
 * @param chart 3x3の盤. 0=空き, 1=プレイヤ1, 2=プレイヤ2
 * @return 勝ったプレイヤ番号(1 or 2). 勝敗が決して居ない場合は 0.
 */
int judgment(int[][] chart) {
    return 0;
}


という雛形が作れるだけの情報が決まったことになります.
後はこの中を書くだけです.
全てを考えると面倒なので 1列だけ考えます.
chart[0][0] = 1 かつ chart[0][1] = 1 かつ chart[0][2] = 1 なら 1 の勝ち.
それをそのまま if 文で書きます.

/**
 * 勝敗を判定します.
 * @param chart 3x3の盤. 0=空き, 1=プレイヤ1, 2=プレイヤ2
 * @return 勝ったプレイヤ番号(1 or 2). 勝敗が決して居ない場合は 0.
 */
int judgment(int[][] chart) {
    if(chart[0][0] == 1 & chart[0][1] == 1 & chart[0][2] == 1) return 1;
    return 0;
}


2つ目3つ目も同様です.
chart[1][0] = 1 かつ chart[1][1] = 1 かつ chart[1][2] = 1 なら 1 の勝ち.
chart[2][0] = 1 かつ chart[2][1] = 1 かつ chart[2][2] = 1 なら 1 の勝ち.

/**
 * 勝敗を判定します.
 * @param chart 3x3の盤. 0=空き, 1=プレイヤ1, 2=プレイヤ2
 * @return 勝ったプレイヤ番号(1 or 2). 勝敗が決して居ない場合は 0.
 */
int judgment(int[][] chart) {
    if(chart[0][0] == 1 & chart[0][1] == 1 & chart[0][2] == 1) return 1;
    if(chart[1][0] == 1 & chart[1][1] == 1 & chart[1][2] == 1) return 1;
    if(chart[2][0] == 1 & chart[2][1] == 1 & chart[2][2] == 1) return 1;
    return 0;
}


縦(横)が出来たら次は横(縦) です.

/**
 * 勝敗を判定します.
 * @param chart 3x3の盤. 0=空き, 1=プレイヤ1, 2=プレイヤ2
 * @return 勝ったプレイヤ番号(1 or 2). 勝敗が決して居ない場合は 0.
 */
int judgment(int[][] chart) {
    if(chart[0][0] == 1 & chart[0][1] == 1 & chart[0][2] == 1) return 1;
    if(chart[1][0] == 1 & chart[1][1] == 1 & chart[1][2] == 1) return 1;
    if(chart[2][0] == 1 & chart[2][1] == 1 & chart[2][2] == 1) return 1;
    if(chart[0][0] == 1 & chart[1][0] == 1 & chart[2][0] == 1) return 1;
    if(chart[0][1] == 1 & chart[1][1] == 1 & chart[2][1] == 1) return 1;
    if(chart[0][2] == 1 & chart[1][2] == 1 & chart[2][2] == 1) return 1;
    return 0;
}


斜めもあります.

/**
 * 勝敗を判定します.
 * @param chart 3x3の盤. 0=空き, 1=プレイヤ1, 2=プレイヤ2
 * @return 勝ったプレイヤ番号(1 or 2). 勝敗が決して居ない場合は 0.
 */
int judgment(int[][] chart) {
    if(chart[0][0] == 1 & chart[0][1] == 1 & chart[0][2] == 1) return 1;
    if(chart[1][0] == 1 & chart[1][1] == 1 & chart[1][2] == 1) return 1;
    if(chart[2][0] == 1 & chart[2][1] == 1 & chart[2][2] == 1) return 1;
    if(chart[0][0] == 1 & chart[1][0] == 1 & chart[2][0] == 1) return 1;
    if(chart[0][1] == 1 & chart[1][1] == 1 & chart[2][1] == 1) return 1;
    if(chart[0][2] == 1 & chart[1][2] == 1 & chart[2][2] == 1) return 1;
    if(chart[0][0] == 1 & chart[1][1] == 1 & chart[2][2] == 1) return 1;
    if(chart[0][2] == 1 & chart[1][1] == 1 & chart[2][0] == 1) return 1;
    return 0;
}


これでプレイヤ1の勝利判定が出来ました. 次にプレイヤ2 は…プレイヤ1の判定をコピペして1を2に書き換えます.

/**
 * 勝敗を判定します.
 * @param chart 3x3の盤. 0=空き, 1=プレイヤ1, 2=プレイヤ2
 * @return 勝ったプレイヤ番号(1 or 2). 勝敗が決して居ない場合は 0.
 */
int judgment(int[][] chart) {
    if(chart[0][0] == 1 & chart[0][1] == 1 & chart[0][2] == 1) return 1;
    if(chart[1][0] == 1 & chart[1][1] == 1 & chart[1][2] == 1) return 1;
    if(chart[2][0] == 1 & chart[2][1] == 1 & chart[2][2] == 1) return 1;
    if(chart[0][0] == 1 & chart[1][0] == 1 & chart[2][0] == 1) return 1;
    if(chart[0][1] == 1 & chart[1][1] == 1 & chart[2][1] == 1) return 1;
    if(chart[0][2] == 1 & chart[1][2] == 1 & chart[2][2] == 1) return 1;
    if(chart[0][0] == 1 & chart[1][1] == 1 & chart[2][2] == 1) return 1;
    if(chart[0][2] == 1 & chart[1][1] == 1 & chart[2][0] == 1) return 1;
    if(chart[0][0] == 2 & chart[0][1] == 2 & chart[0][2] == 2) return 2;
    if(chart[1][0] == 2 & chart[1][1] == 2 & chart[1][2] == 2) return 2;
    if(chart[2][0] == 2 & chart[2][1] == 2 & chart[2][2] == 2) return 2;
    if(chart[0][0] == 2 & chart[1][0] == 2 & chart[2][0] == 2) return 2;
    if(chart[0][1] == 2 & chart[1][1] == 2 & chart[2][1] == 2) return 2;
    if(chart[0][2] == 2 & chart[1][2] == 2 & chart[2][2] == 2) return 2;
    if(chart[0][0] == 2 & chart[1][1] == 2 & chart[2][2] == 2) return 2;
    if(chart[0][2] == 2 & chart[1][1] == 2 & chart[2][0] == 2) return 2;
    return 0;
}


これで judgment が出来ました. main から呼び出せば, 勝敗が返されます.
...
おそらく「こんな並べただけのコードは格好悪くてイヤだ」と思われるでしょう.
では「機能が変わらないように」書き方を変えてみましょう.
まずはプレイヤ1とプレイヤ2の判定の違いをループに出来ます.

/**
 * 勝敗を判定します.
 * @param chart 3x3の盤. 0=空き, 1=プレイヤ1, 2=プレイヤ2
 * @return 勝ったプレイヤ番号(1 or 2). 勝敗が決して居ない場合は 0.
 */
int judgment(int[][] chart) {
    for(int player=1; player<=2; player++) {
        if(chart[0][0] == player & chart[0][1] == player & chart[0][2] == player) return player;
        if(chart[1][0] == player & chart[1][1] == player & chart[1][2] == player) return player;
        if(chart[2][0] == player & chart[2][1] == player & chart[2][2] == player) return player;
        if(chart[0][0] == player & chart[1][0] == player & chart[2][0] == player) return player;
        if(chart[0][1] == player & chart[1][1] == player & chart[2][1] == player) return player;
        if(chart[0][2] == player & chart[1][2] == player & chart[2][2] == player) return player;
        if(chart[0][0] == player & chart[1][1] == player & chart[2][2] == player) return player;
        if(chart[0][2] == player & chart[1][1] == player & chart[2][0] == player) return player;
    }
    return 0;
}


ここからどうしましょう. chart の添え字が 0,1,2 と変わっているだけの違いの箇所があるので, まとめてみます.

/**
 * 勝敗を判定します.
 * @param chart 3x3の盤. 0=空き, 1=プレイヤ1, 2=プレイヤ2
 * @return 勝ったプレイヤ番号(1 or 2). 勝敗が決して居ない場合は 0.
 */
int judgment(int[][] chart) {
    for(int player=1; player<=2; player++) {
        for(int i=0; i<3; i++) {
            if(chart[i][0] == player & chart[i][1] == player & chart[i][2] == player) return player;
            if(chart[0][i] == player & chart[1][i] == player & chart[2][i] == player) return player;
        }
        if(chart[0][0] == player & chart[1][1] == player & chart[2][2] == player) return player;
        if(chart[0][2] == player & chart[1][1] == player & chart[2][0] == player) return player;
    }
    return 0;
}


まだ少し気持ち悪さがありますが, これ以上は大分形が変わると思いますのでここまでにします.

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

0

質問のコードは重複が多かったので、重複を少なくすることと、勝敗判定メソッド追加をしてみました。
chart には 0, 1, 2 でなく 0, -1, 1 を入れるようにして、player の交代を * (-1) でできるようにしています。
勝敗判定は、勝敗をチェックするマス目の列をデータ文にして、そのデータを使って破綻するようにしてみました。

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;

public class Example2XX {
    static final int DIM = 3;
    static final String[] MARKS = { "○", "・", "✗" };
    static int[][] chart = new int[DIM][DIM]; // 〇×の盤
    static BufferedReader br = new BufferedReader(new InputStreamReader(System.in));

    public static void main(String args[]) throws IOException {
        int player = -1; // -1: ○, 1: ✗
        int result = 0;
        for (int i = 0; i < DIM * DIM && (result == 0); i++) {
            result = play_hand(player);
            player *= -1;
        }
        show_result(result);
    }

    static int play_hand(int player) throws IOException {
        while (true) {
            int col = input_number("列番号入力:");
            int row = input_number("行番号入力:");
            if (chart[row][col] == 0) { // 置きたい場所が空いているか?
                chart[row][col] = player;
                show_board();
                return judge();
            }
        }
    }

    // 盤表示
    static void show_board() {
        String lines = "";
        for (int x = 0; x < DIM; x++) {
            for (int y = 0; y < DIM; y++) {
                lines += MARKS[chart[x][y] + 1];
            }
            lines += "\n";
        }
        System.out.print(lines);
    }

    static int input_number(String message) throws IOException {
        // 数字入力
        int num = 0;
        System.out.print(message);
        while (true) {
            try {
                num = Integer.parseInt(br.readLine());
                if ((1 <= num) && (num <= DIM)) {
                    return num - 1;
                }
            } catch (NumberFormatException e) {
            }
            System.out.print("1から" + DIM + "の数字を入力してください:");
        }
    }

    static void show_result(int result) {
        if ( result == 0) {
            System.out.println("引き分けです。");
        } else {
            String winer = (result == -1) ? MARKS[0] : MARKS[2];
            System.out.println(winer + "の勝ちです。");
        }
    }

    static int judge() {
        // 勝敗を判定するマス位置の列を列挙
        int[][][] check_lines = { 
                { { 0, 0 }, { 0, 1 }, { 0, 2 } }, 
                { { 1, 0 }, { 1, 1 }, { 1, 2 } },
                { { 2, 0 }, { 2, 1 }, { 2, 2 } }, 
                { { 0, 0 }, { 1, 0 }, { 2, 0 } }, 
                { { 0, 1 }, { 1, 1 }, { 2, 1 } },
                { { 0, 2 }, { 1, 2 }, { 2, 2 } },
                { { 0, 0 }, { 1, 1 }, { 2, 2 } }, 
                { { 2, 0 }, { 1, 1 }, { 0, 2 } }
        };
        for (int[][] pos : check_lines) {
            int v0 =  chart[pos[0][0]][pos[0][1]];
            int v1 =  chart[pos[1][0]][pos[1][1]];
            int v2 =  chart[pos[2][0]][pos[2][1]];
            if ((v0 != 0) && (v0 == v1) && (v0 == v2)) {
                return v0; // 勝負あり
            }
        }
       return 0; // 引き分け
    }
}

実行例
イメージ説明

tictactow java
で google 検索すると、いろいろなプログラム例を見つけることができると思います。

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

15分調べてもわからないことは、teratailで質問しよう!

  • ただいまの回答率 87.37%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

同じタグがついた質問を見る