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

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

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

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

Q&A

解決済

2回答

844閲覧

Javascript 簡易ゲーム if文の書き方とalertに配列の値を表示させたい

hiro_ike

総合スコア48

JavaScript

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

0グッド

0クリップ

投稿2021/05/04 00:25

編集2021/05/04 02:05

初心者でJavaScript学習のために作成してます。
分かるところから、自分で書いており、途中のものになります。。
if文が苦手で、アドバイスいただけますと幸いです。

前提:
自分の船(ourHero)
ヒットポイント - 20
攻撃するパワー - 5
攻撃が当たる確率 - 0.7

敵の船
ヒットポイント - 3 〜 6の乱数
攻撃するパワー - 2 〜 4の乱数
攻撃が当たる確率 - 0.6 〜 0.8の乱数

上記の数値のもと、攻撃し、され、
ヒットポイントが残っていれば、戦い続け、
ゼロになったら、再度攻撃するか、敗退するか選択するstartprompt()に戻るように書きたい。

下記2点につまづきました。

1) alert内で配列の値を表示させたい。
-> 以前、別のコードを書いた時は下記で表示されたのですが、今回はうまく表示できていないので、
ご指摘いただけますと幸いです。

alert('敵から攻撃をうけた!' + ${tekiArray[0]accuracy}' + ' ${ourHero.hitPoints}');
  1. 敵の船の手持ちのヒットポイントが0になったら、ゲームを開始するか否かのstartPrompt()関数へ飛ばしたいと思っています。

なんとなく下記の書き方は間違っていると思うので、アドバイスいただけますと幸いです。

} else if ( tekiArray[0].hitPoints = 0 ){ alert('敵の船の破壊に成功!'); startPrompt();

自分で書き進めたところ↓

class Ship{ constructor(hitPoints, firepower, accuracy){ this.hitPoints = hitPoints; this.firepower = firepower; this.accuracy = accuracy; } } //hitPoints, firepower, accuracy const ourHero = new Ship(20, 5, 0.7); class tekiShip extends Ship{ constructor(hitPoints, firepower, accuracy){ super(hitPoints, firepower, accuracy); } } let tekiArray = [] for(let i =0; i < 6; i++){ tekiArray[i] = new tekiShip (randomizer(3,6), randomizer(2,4),(randomizer(60,80) / 100)); } console.log(tekiArray) function randomizer(min, max){ return (Math.floor(Math.random() * (max - min + 1) + min)); } function game(){ playGame = prompt('Y を入力してゲームを開始する'); playGame = playGame.toUpperCase(); if (playGame === 'Y'){ startPrompt() } else { alert('またね') } function startPrompt(){ let ans; while(true) { ans = getCommand(); if (ans == '') continue; if (ans == 'attack') { doBattle(); } else { alert('Game Over・゚。(´;д;`) 。゚・Game Over'); } break; } } function getCommand() { const cmd = prompt('"attack" or "retreat"を入力してください'); let ret = cmd.toLowerCase(); if (ret != 'attack' && ret != 'retreat') ret = ''; return ret; } function doBattle(){ while (true){ if (Math.random() < tekiArray[0].accuracy) { ourHero.hitPoints -= tekiArray[0].firepower; console.log(ourHero.hitPoints) alert('敵から攻撃を受けた' + ' ${tekiArray[0]accuracy}' + '${ourHero.hitPoints}'); } else if (Math.random() < ourHero.accuracy){ tekiArray[0].hitPoints -= ourHero.firepower; alert("敵に攻撃を仕掛けた"); } else if ( tekiArray[0].hitPoints = 0 ){ alert('敵の船の破壊に成功!'); startPrompt(); break; } } }} game(); startPrompt();

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

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

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

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

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

m.ts10806

2021/05/04 00:33

タイトルと質問内容が大きく離れているように思います。 タイトルには要件を、起きている問題詳細・課題などを記載してください。 https://teratail.com/help/question-tips#questionTips3-1 このままだと要件変わったにも関わらず同じタイトルで投稿続けることになります。
hiro_ike

2021/05/04 01:10

ご指摘ありがとうございます。 タイトルを更新してみました。
coolwind0202

2021/05/04 01:23

1) ・配列の内容を表示させたいとありますが、ourHero.hitPoints は配列ではないと思います ・うまく表示できていない というのが不明瞭なので、「どういう表示を期待して」「実際にはどういう表示」だったのか知りたいです
hiro_ike

2021/05/04 02:10

ご確認ありがとうございます。一部漏れていたので追記しました。 ${tekiArray[0]accuracy}' + '${ourHero.hitPoints}' 上記のように書くと、現状、この文字列のままalertに表示されます。 やりたいこと: テストするためにも、処理/計算時の実際の値を目視したい。というのが目的でした。 初心者のため、多分該当箇所の書き方に問題があると思い、質問させていただきました。
coolwind0202

2021/05/04 02:29

「else」を使って書かれているようですが、以下の3つの状況は同時に起こり得ますか? 「敵から攻撃を受けた」「敵に攻撃を仕掛けた」「敵の船の破壊に成功した」 敵に攻撃を仕掛けた直後に敵の船の破壊に成功することは、あり得るのではないですか?
hiro_ike

2021/05/04 03:02

ご確認ありがとうございます。 仰る通り、有り得ますね。。 こういった場合、全てifで書き始めたら良いのでしょうか?
guest

回答2

0

ベストアンサー

1)テンプレートリテラルの使い方について

  • 文字列を ' ではなく ` で囲います
  • 変数名を ${} で囲います

js

1alert('敵から攻撃をうけた!' + ${tekiArray[0]accuracy}' + ' ${ourHero.hitPoints}');

js

1 2alert(`敵から攻撃をうけた! ${tekiArray[0].accuracy} ${ourHero.hitPoints}`);

2)

敵の船の手持ちのヒットポイントが0になったら 必ず敵の船のヒットポイントが0になるとは限らないと思います。
また、if 文の条件式が true と判断されると、以降の else はまったく実行されません。
なので、

js

1if (Math.random() < tekiArray[0].accuracy) { 2 alert('敵から攻撃を受けた' + ' ${tekiArray[0]accuracy}' + '${ourHero.hitPoints}'); 3} else if (Math.random() < ourHero.accuracy){ 4 alert("敵に攻撃を仕掛けた"); 5} else if ( tekiArray[0].hitPoints = 0 ){ 6 alert('敵の船の破壊に成功!'); 7}

このとき、敵の accuracy と 自身の accuracy の両方が Math.random() 以下にならないと、敵の船の破壊は永遠に通知されません。
これらを踏まえて、以下のように変更しました。

js

1if (Math.random() < tekiArray[0].accuracy) { 2 ourHero.hitPoints -= tekiArray[0].firepower; 3 console.log(ourHero.hitPoints) 4 alert(`敵から攻撃をうけた! ${tekiArray[0].accuracy} ${ourHero.hitPoints}`); 5} 6if (Math.random() < ourHero.accuracy){ 7 tekiArray[0].hitPoints -= ourHero.firepower; 8 alert("敵に攻撃を仕掛けた"); 9} 10if ( tekiArray[0].hitPoints <= 0 ){ 11 alert('敵の船の破壊に成功!'); 12 startPrompt(); 13 break; 14}

投稿2021/05/04 03:17

coolwind0202

総合スコア708

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

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

coolwind0202

2021/05/04 03:17

仕様を把握しきれていないので、もし不足している点があればお知らせください。
hiro_ike

2021/05/04 05:30

ありがとうございます! 最後に一つだけ、もしお分かりになりましたら、教えて頂きたいです。 敵のShip一船を倒したら、 startPrompt()へ戻り、 attackを入力したら、 残りの船を倒していくようなフローにしたいのですが、 この時は、どのように指定したら良いでしょうか? m(_ _)m
coolwind0202

2021/05/04 06:33

いまのコードでは、常に tekiArray の最初の要素を敵の現在の船として使用しています。 フローの実現方法として考えられるのは、現在の船の配列内でのインデックスを示す変数を用意することです。 たとえば、変数「currentTekiIndex = 0」を定義すると、現在の敵船オブジェクトは tekiArray[currentTekiIndex] と取得できますし、現在の敵船のヒットポイントが0以下になったら currentTekiIndex++; を実行することで、攻撃対象を次の船に変更できます。
hiro_ike

2021/05/04 19:04

>現在の船の配列内でのインデックスを示す変数を用意すること こちらは、下記に追加するということでしょうか? let tekiArray = [] for(let i =0; i < 6; i++){ tekiArray[i] = new tekiShip (randomizer(3,6), randomizer(2,4),(randomizer(60,80) / 100)); }
coolwind0202

2021/05/05 01:37

関数の外ならどこでも良いと思いますよ
hiro_ike

2021/05/05 04:06

やりたいことが出来ました! 後ほどコード載せます。
guest

0

JavaScript

1class Ship { 2 constructor(hitPoints, firepower, accuracy) { 3 this.hitPoints = hitPoints; 4 this.firepower = firepower; 5 this.accuracy = accuracy; 6 } 7} 8 9//hitPoints, firepower, accuracy 10const ourHero = new Ship(20, 5, 0.7); 11 12class tekiShip extends Ship { 13 constructor(hitPoints, firepower, accuracy) { 14 super(hitPoints, firepower, accuracy); 15 } 16} 17let tekiArray = [] 18for (let i = 0; i < 6; i++) { 19 tekiArray[i] = new tekiShip(randomizer(3, 6), randomizer(2, 4), (randomizer(60, 80) / 100)); 20} 21console.log(tekiArray) 22 23function randomizer(min, max) { 24 return (Math.floor(Math.random() * (max - min + 1) + min)); 25} 26 27function game() { 28 playGame = prompt('ゲームを開始するには、Yを入力してください'); 29 playGame = playGame.toUpperCase(); 30 if (playGame === 'Y') { 31 startPrompt() 32 } else { 33 alert('GoodBye') 34 } 35 36 function startPrompt() { 37 let ans; 38 while (true) { 39 ans = getCommand(); 40 if (ans == '') continue; 41 if (ans == 'attack') { 42 doBattle(); 43 } else { 44 alert('Game Over・゚。(´;д;`) 。゚・Game Over'); 45 } 46 break; 47 } 48 } 49 50 function getCommand() { 51 const cmd = prompt('Enter "attack" or "retreat"'); 52 if (cmd === null) return 53 let ret = cmd.toLowerCase(); 54 if (ret != 'attack' && ret != 'retreat') ret = ''; 55 return ret; 56 } 57 58 function doBattle() { 59 while (tekiArray.length) { 60 if (Math.random() < tekiArray[0].accuracy) { 61 ourHero.hitPoints -= tekiArray[0].firepower; 62 console.log(ourHero.hitPoints) 63 alert(`攻撃を受けた ${tekiArray[0].accuracy} ${ourHero.hitPoints}`); 64 } 65 if (Math.random() < ourHero.accuracy) { 66 tekiArray[0].hitPoints -= ourHero.firepower; 67 alert(`攻撃を仕掛けた ${tekiArray[0].accuracy} ${ourHero.hitPoints}`); 68 } 69 if (tekiArray[0].hitPoints <= 0) { 70 alert(`You destroyed the ship successfully!`); 71 tekiArray.shift(); 72 if (!tekiArray.length){ 73 console.log("(๑˃̵ᴗ˂̵)و 勝利!! (๑˃̵ᴗ˂̵)و ") 74 }else { 75 startPrompt() 76 } 77 } 78 if (this.hitPoints <= 0) { 79 alert("Game Over・゚。(´;д;`) 。゚・Game Over!"); 80 startPrompt(); 81 } 82 } 83 } 84} 85game();

投稿2021/05/05 16:15

編集2021/05/05 18:56
hiro_ike

総合スコア48

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

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

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.35%

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

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

質問する

関連した質問