目次
はじめに
Paizaにてスキルチェック見本問題(PHP編)を解いてみました。
本番問題の解答・解説はNGですが、見本問題に関しては、公開していいそうなのでまとめておきます。
(回答をPaizaでは再度閲覧できないため、備忘録的目的もあります。また、現状ランクB以上の問題を解くだけの能力はないためランクCまでのまとめになります。精進・・・)
また、事前知識として標準入力の基本を知っておく必要がありますが、今回は割愛します。以下が参考になるかと思います。
https://paiza.jp/works/search_chapters/3003
追記:標準入力についてまとめました。
①掛け算 (paizaランク D 相当)
以下が問題のリンクです。詳細はこちらでご確認ください。
https://paiza.jp/works/mondai/skillcheck_sample/multiplication?language_uid=php
実際に入力される値: 2 3
期待される出力: 6
解答コード: <?php $a = fgets(STDIN); //1行目の標準入力の値を$aに代入 $b = fgets(STDIN); //2行目の標準入力の値を$bに代入 echo $a*$b; //出力 ?>
初学者がPaizaで標準入力を勉強した場合はおそらく、fgets関数を用いたこの解答になるんじゃないかと思います。(僕もそうでした。)
解答コード(別パターン): <?php fscanf(STDIN, "%d", $a); //1行目の標準入力の値を$aに代入 fscanf(STDIN, "%d", $b); //2行目の標準入力の値を$bに代入 echo $a*$b; //出力 ?>
こちらは別パターン。一応こちらでも正解になります。
AtCoder(Paizaと同じような問題に取り組める競技プログラミングサイト)に挑戦し始めると、知ることになるであろうfscanf関数を用いた解答です。
fscanf関数を用いると1行に値が2つスペース区切りである際などに威力を発揮しますので、次の問題を例にまとめます。
②足し算 (paizaランク D 相当)
以下が問題のリンクです。詳細はこちらでご確認ください。
https://paiza.jp/works/mondai/skillcheck_sample/addition?language_uid=php
実際に入力される値: 1 1
期待される出力: 2
解答コード: <?php $numbers = fgets(STDIN); //$numbersに1 1が代入される $number = explode(" ",$numbers); //$numbersをスペースで分割して$numberの通常配列を作成 echo $number[0]+$number[1]; //配列のインデックス番号を指定して要素を取り出し、計算後、出力 ?>
fgets関数を用いた場合は、explode関数で文字列を分割して配列を作ります。
解答コード(別パターン): <?php fscanf(STDIN, "%d %d", $a, $b); echo $a+$b; ?>
こちらがfscanf関数を用いた解答パターン。
個人的には、配列を作らずに変数にダイレクトに値を代入&取り出しができるので、理解がし易いコードになりました。
%dで引数は数値として扱われます。
以下、参考にした公式ドキュメントのリンクです。
https://www.php.net/manual/ja/function.fscanf.php
③一番小さい値 (paizaランク D 相当)
以下が問題のリンクです。詳細はこちらでご確認ください。
https://paiza.jp/works/mondai/skillcheck_sample/min_num?language_uid=php
実際に入力される値: 10 12 4 8 46
期待される出力: 4
解答コード: <?php $a = fgets(STDIN); $b = fgets(STDIN); $c = fgets(STDIN); $d = fgets(STDIN); $e = fgets(STDIN); $array = array((int)$a,(int)$b,(int)$c,(int)$d,(int)$e); echo min($array); ?>
解答コード(別パターン): <?php $a = (int)fgets(STDIN); $b = (int)fgets(STDIN); $c = (int)fgets(STDIN); $d = (int)fgets(STDIN); $e = (int)fgets(STDIN); $array = array($a,$b,$c,$d,$e); echo min($array); ?>
※確実にもっとシンプルにコード書ける・・・教えてください・・・(追記しました。)
最大値・最小値を求める PHP の組込み関数、min
を利用しています。
(int)
を記載しないと文字型(string)として扱ってしまうため記載。
演算に関しては文字列も自動的に数値として扱ってくれるため、①②に関しては(int)の記載が不要でした。
(以下、追記)
<?php for($i=0;$i<5;$i++){ $number = (int)fgets(STDIN); $numbers[] = $number; } echo min($numbers); ?>
この書き方でだいぶすっきりしました。
問題文で5つと値の数が指定されているので、for文で5回繰り返し値を配列に代入してあげればOKです。
④文字の一致 (paizaランク D 相当)
以下が問題のリンクです。詳細はこちらでご確認ください。
https://paiza.jp/works/mondai/skillcheck_sample/diff_str?language_uid=php
実際に入力される値: paiza paiza
期待される出力: OK
解答コード: <?php $a = trim(fgets(STDIN)); $b = trim(fgets(STDIN)); if($a === $b){ echo "OK"; }else{ echo "NG"; } ?>
意図しない改行や空白の代入を防ぐためにtrim()を記載しています。
※記載しなくても正解になるのですが、var_dump($a);で出力すると改行が代入されていることがわかります。
解答コード(別パターン): <?php fscanf(STDIN, "%s", $a); fscanf(STDIN, "%s", $b); if($a === $b){ echo "OK"; }else{ echo "NG"; } ?>
こちらはfscanf関数を用いたケース。引数を文字型として扱いたいので%s
で記載しています。
⑤数の並び替え (paizaランク D 相当)
以下が問題のリンクです。詳細はこちらでご確認ください。
https://paiza.jp/works/mondai/skillcheck_sample/sort-number?language_uid=php
実際に入力される値: 5 3 5 19 1 2
期待される出力: 1 2 3 5 19
解答コード: <?php $n = fgets(STDIN); //1行目で入力される正の整数nを$nへ代入 while ($number = fgets(STDIN)) { $numbers[] = $number; //while文で2行目以降の標準入力値を$numbersへ配列にして代入 sort( $numbers, SORT_NUMERIC ); //配列の値を並び替えます。 } $i = 0; while ($i < $n){ echo $numbers[$i]; $i++; } ?>
解答コード(別パターン): <?php $n = fgets(STDIN); for ($i=0;$i<$n;$i++){ $number = fgets(STDIN); $numbers[] = $number; sort( $numbers, SORT_NUMERIC ); } for ($i=0;$i<$n;$i++){ echo $numbers[$i]; } ?>
ここから繰り返し処理のwhile文、for文の知識が必要になってきますね。
個人的にはfor文の方が処理の理解がしやすい気がします。
おわりに
Paizaで提出したコードは再度閲覧が不可能なので、どこかにまとめておく必要があるかと思いました。
実際に、この記事を書く際に再度コードを書き直しました。。。
(結果的に、効率の良い書き方を見つけられたのでよかったが。)
現在、ランクCなのでとりあえずランクBになれるよう頑張ります。
関連リンク
Paiza スキルチェック見本問題(PHP編)まとめ ~ランクC相当~
https://chobimusic.com/paiza_skillcheck_c/
コメントを残す