【危機感】ミュータブルとイミュータブルについて曖昧だと危ない!!![JavaScript][PHP]
日常会話でミュータブル、イミュータブルって使わないですよね。実はイミュータブルには恐ろしい罠が潜んでいるのです。。。実例と共に深掘りしていきましょー
この機会に公式ドキュメントから読み解いて理解を深めるゾイ
ミュータブル、イミュータブルってなんぞ?
まずは公式のMDNから引用します。
では読み解いて行きましょう!
先頭から
PHPの書き方については後ほど登場します!
まずはJavaScriptで理解を深めて行きましょう!
JavaScriptのプリミティブ === イミュータブルです。
以下のコードの変数たちがまさにイミュータブル
JavaScriptだとミュータブルな値は具体的には以下の感じ
この上記の文がやっかいで理解してないと意図しないバグ混入の恐れがあります😰
以下のコードではmyObjのnameプロパティを変更して新しくnewMyObjというオブジェクトを作成しています。
求める仕様
太郎の名前を含んだオブジェクトと二郎の名前を含んだオブジェクトを出力する
出力結果は以下のようになります。
myObj: {name: "二郎", score:100}
newMyObj: {name:"二郎", score:100}
変更を加えたいのがnewMyObjだけなのにmyObjの値まで変更されてしまいます(@_@)
なんでオブジェクトや配列を扱うときは
上記一行みたいに気軽にオブジェクトに直接渡すのはバグの元になります💦
対策
JavaScriptでは3行目のスプレッド演算子(3点ドットのこと)を用いた書き方をすることで簡単に別のオブジェクトとして扱うことができます。(これは配列でも同様です)またこのようなコピーのことをディープコピーと言います。
PHPだとどう書くの?
まずは、ミュータブルの危険性を意識していない以下のコードから確認しましょう
上記コードでは、トランプカードゲームの戦争を管理するGameManagerクラスの中のplayメソッドです。
playメソッドについて
playメソッドではゲームを開始してゲーム終了するまでの処理を担います。
6行目の
のようなコードを放置していると、candidateWinnerPlayersだけで変更したかった条件がいつのまにかplayersにも影響を与えてしまい、意図しない挙動を生む可能性があります💦
対策
上記のようにclone関数を用いることで$playerインスタンスをディープコピーします。これにより$candidateWinnerPlayersが変更されても$playersに影響しないので安全にインスタンスがちゃがちゃできるようになりますd(^_^o)
ミュータブル、イミュータブルを極めて安全な開発ライフを送りましょう!!!