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

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

新規登録して質問してみよう
ただいま回答率
85.48%
JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

React.js

Reactは、アプリケーションのインターフェースを構築するためのオープンソースJavaScriptライブラリです。

Q&A

解決済

1回答

693閲覧

直前のstateを取得したい

退会済みユーザー

退会済みユーザー

総合スコア0

JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

React.js

Reactは、アプリケーションのインターフェースを構築するためのオープンソースJavaScriptライブラリです。

0グッド

0クリップ

投稿2020/01/27 13:18

編集2020/01/27 15:29

Reactでオセロを作成しているのですが、

js

1import React, { useState } from 'react' 2import Square from '../Square' 3import styles from './styles' 4 5const { Status, BoardRow } = styles 6 7const BLACK_PIECE = 'black' 8const WHITE_PIECE = 'white' 9 10let defaultBoard = new Array(8) 11for (let i = 0; i < defaultBoard.length; i++) { 12 defaultBoard[i] = new Array(8) 13} 14 15for (let x = 0; x < 8; x++) { 16 for (let y = 0; y < 8; y++) { 17 defaultBoard[x][y] = null 18 } 19} 20 21// defaultBoard[3][3] = BLACK_PIECE 22// defaultBoard[4][3] = WHITE_PIECE 23// defaultBoard[3][4] = WHITE_PIECE 24// defaultBoard[4][4] = BLACK_PIECE 25 26defaultBoard[0][0] = WHITE_PIECE 27defaultBoard[1][0] = BLACK_PIECE 28defaultBoard[2][0] = WHITE_PIECE 29defaultBoard[3][0] = WHITE_PIECE 30 31defaultBoard[5][0] = WHITE_PIECE 32defaultBoard[6][0] = WHITE_PIECE 33defaultBoard[7][0] = WHITE_PIECE 34 35// defaultBoard[4][1] = WHITE_PIECE 36// defaultBoard[4][2] = WHITE_PIECE 37// defaultBoard[4][3] = WHITE_PIECE 38// defaultBoard[4][4] = WHITE_PIECE 39// defaultBoard[4][5] = WHITE_PIECE 40// defaultBoard[4][6] = BLACK_PIECE 41// defaultBoard[4][7] = WHITE_PIECE 42 43// defaultBoard[3][1] = WHITE_PIECE 44// defaultBoard[2][2] = WHITE_PIECE 45// defaultBoard[1][3] = BLACK_PIECE 46// defaultBoard[0][4] = WHITE_PIECE 47 48// defaultBoard[5][1] = WHITE_PIECE 49// defaultBoard[6][2] = WHITE_PIECE 50// defaultBoard[7][3] = WHITE_PIECE 51 52const Board = () => { 53 const [squares, setSquares] = useState(defaultBoard) 54 const [currentPiece, setCurrentPiece] = useState(BLACK_PIECE) 55 const status = 'Next player: ' + (currentPiece === BLACK_PIECE ? '黒の番' : '白の番'); 56 57 const boardInit = () => { 58 if (!window.confirm('リセットしてもよろしいですか?')) { 59 return false 60 } 61 62 for (let x = 0; x < 8; x++) { 63 for (let y = 0; y < 8; y++) { 64 let newSquares = squares.concat() 65 newSquares[x][y] = null 66 setSquares(newSquares) 67 } 68 } 69 let newSquares = squares.concat() 70 newSquares[3][3] = BLACK_PIECE 71 newSquares[4][3] = WHITE_PIECE 72 newSquares[3][4] = WHITE_PIECE 73 newSquares[4][4] = BLACK_PIECE 74 setCurrentPiece(BLACK_PIECE) 75 setSquares(newSquares) 76 } 77 78 const reversePiece = (currentX, currentY, x, y) => { 79 const nextPiece = currentPiece === BLACK_PIECE ? WHITE_PIECE : BLACK_PIECE 80 let newSquares = squares.concat() 81 let nextYIndex = currentY + y 82 let nextXIndex = currentX + x 83 84 if (newSquares[nextYIndex][nextXIndex] === nextPiece) { 85 newSquares[currentY][currentX] = currentPiece 86 87 while(true) { 88 if (newSquares[nextYIndex][nextXIndex] === currentPiece) { 89 setCurrentPiece(nextPiece) 90 setSquares(newSquares) 91 break 92 } 93 if (newSquares[nextYIndex][nextXIndex] === null) { 94 // breakする前に元の配列に戻す 95 setSquares(squares) 96 break 97 } 98 newSquares[nextYIndex][nextXIndex] = currentPiece 99 nextYIndex = nextYIndex + y 100 nextXIndex = nextXIndex + x 101 if (nextYIndex > 7 || nextYIndex < 0 || nextXIndex > 7 || nextXIndex < 0) { 102 // breakする前に元の配列に戻す 103 setSquares(squares) 104 break 105 } 106 } 107 } 108 } 109 110 const handleClick = (x, y) => { 111 if (squares[y][x] === null) { 112 // reversePiece(x, y, 1, 0) // 右 113 reversePiece(x, y, 0, 1) // 下 114 reversePiece(x, y, 0, -1) // 上 115 // reversePiece(x, y, 1, 1) // 右下 116 // reversePiece(x, y, 1, -1) // 右上 117 // reversePiece(x, y, -1, 0) // 左 118 // reversePiece(x, y, -1, 1) // 左下 119 // reversePiece(x, y, -1, -1) // 左上 120 } 121 } 122 123 // 縦軸y, 横軸x 124 const renderSquare = (boardRow, y) => { 125 return ( 126 boardRow[y].map((square, x) => { 127 return ( 128 <Square 129 square={ square } 130 key={ x } 131 addValue={ () => handleClick(x, y) } 132 /> 133 ) 134 }) 135 ) 136 } 137 138 return ( 139 <> 140 <button 141 onClick={ boardInit } 142 > 143 最初からやり直す 144 </button> 145 <Status>{ status }</Status> 146 <BoardRow> 147 { renderSquare(defaultBoard, 0) } 148 </BoardRow> 149 <BoardRow> 150 { renderSquare(defaultBoard, 1) } 151 </BoardRow> 152 <BoardRow> 153 { renderSquare(defaultBoard, 2) } 154 </BoardRow> 155 <BoardRow> 156 { renderSquare(defaultBoard, 3) } 157 </BoardRow> 158 <BoardRow> 159 { renderSquare(defaultBoard, 4) } 160 </BoardRow> 161 <BoardRow> 162 { renderSquare(defaultBoard, 5) } 163 </BoardRow> 164 <BoardRow> 165 { renderSquare(defaultBoard, 6) } 166 </BoardRow> 167 <BoardRow> 168 { renderSquare(defaultBoard, 7) } 169 </BoardRow> 170 </> 171 ); 172} 173 174export default Board; 175

実際の画面はこちらです。(裏返すことができるかテストするために駒を様々な箇所に設置しています。)
イメージ説明

上記の記述のうち、クリックした時に駒を裏返すことができるか1マスずつ判定しつつ、以下の2つの条件に当てはまる場合にはまだ裏返されていない直前のstateを反映させたいのですが、

  • 自分のコマと挟み撃ちできていない
  • 自分のコマがないままnullである場合

js

1if (newSquares[nextYIndex][nextXIndex] === null) { 2 // breakする前に元の配列に戻す 3 console.log(squares) //これで調べても裏返ったあとのstate(下記画像のような)しか取得できない 4 setSquares(squares) 5 break 6} 7if (nextYIndex > 7 || nextYIndex < 0 || nextXIndex > 7 || nextXIndex < 0) { 8 // breakする前に元の配列に戻す 9 console.log(squares) //これで調べても裏返ったあとのstate(下記画像のような)しか取得できない 10 setSquares(squares) 11 break 12}

イメージ説明
と下側の駒まで裏返ってしまいます。
なお、一つずつ方向を記述した場合だと成功するので、裏返なかった結果になっても次のメソッドで一緒に反映されてしまうみたいです。
どのように記述すると直前のstateを取得できるのでしょうか。
よろしくお願いします。

気になる質問をクリップする

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

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

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

concatによるコピーはshallow copyなので
二次配列の中身は元の配列への参照のままです
特にクラスオブジェクトとか入ってないならで

js

1let newSquares = JSON.parse(JSON.stringify(squares));

でdeep copy

投稿2020/01/29 07:50

KazuhiroHatano

総合スコア7804

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

退会済みユーザー

退会済みユーザー

2020/01/29 15:26

ありがとうございます。 無事直前のstateを取得することができました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問