コーディング規約に入れるべき決まりはどれかを読みやすさと安全性で考える
基本情報技術者試験 平成30年度秋期 午前 問7 / アルゴリズムとプログラミング › プログラミング
過去問にチャレンジ
プログラムのコーディング規約に規定する事項のうち,適切なものはどれか。
- ア
局所変数は,用途が異なる場合でもデータ型が同じならば,できるだけ同一の変数を使うようにする。
- イ
処理性能を向上させるために,ループの制御変数には浮動小数点型変数を使用する。
- ウ
同様の計算を何度も繰り返すときは,関数の再帰呼出しを用いる。
- エ
領域割付け関数を使用するときは,割付けができなかったときの処理を記述する。
会話形式の解説
講師今回はコーディング規約、つまりチームでコードの書き方をそろえるための決まりについての問題です。各選択肢が「後から読む人が意味を取り違えないか」「実行時に誤差や異常が起きないか」の2点を守れているかで見ていきましょう。
受験者私は、同じデータ型の変数を使い回すという選択肢が少し気になりました。変数の数が減ってすっきりするので、良いことのようにも思えます。
講師数は減りますが、一つの変数が場所によって別の意味を持つことになります。読む人がそこでの値の意味を追えなくなりますし、誤用の原因にもなります。そこで、変数は用途ごとに分け、役割の分かる名前を付けるのが原則です。
受験者読みやすさを損なうので規約としては不適切ということですね。ループの制御変数、つまり繰り返しの回数を数える変数を浮動小数点型にする選択肢は、性能のためと書いてあるので迷いました。
講師そこが引っかけです。浮動小数点型は加算を繰り返すと誤差がたまり、反復回数が意図とずれることがあります。それに、整数型より演算が速いわけでもないので、性能向上の理由にもなりません。制御変数には整数型を使います。
受験者理由として書かれている性能向上の部分も成り立たないのですね。再帰呼出しの選択肢はどうでしょうか。私は再帰の処理を追うのに時間がかかるのですが、短く書けるので推奨されるのかと思っていました。
講師再帰呼出しは、呼出しの深さによってスタックの使用量が変わります。スタックは関数呼出しのたびに情報を積む領域です。その使用量を事前に見積もれないため、あふれてしまうスタックオーバーフローを起こすおそれがあり、規約で再帰を禁止する場合もあります。
受験者では、同じ計算を何度も繰り返したいときはどう書けばよいのですか。
講師再帰ではなく、ループで繰り返すか、共通の処理を通常の関数にまとめて呼び出すのが一般的です。関数にまとめること自体は問題なく、自分自身を呼び出す形にしないという点が違いです。
受験者残るのは、領域割付け関数を使うときに割付けできなかった場合の処理を書くという選択肢ですね。メモリが足りずに確保に失敗することがあるから、ということでしょうか。
講師そのとおりです。失敗に気づかず、確保できていない領域を使うと、後続の処理で異常終了などの障害が起きます。戻り値を確認して失敗時の処理を用意することは、安全性の面から規約で定めるべき事項です。これが正解です。
受験者整理すると、変数の使い回しは読みやすさを損ない、浮動小数点型の制御変数は誤差、再帰はスタックの見積もりができないという問題があり、割付け失敗時の処理だけが安全性を高める決まりということですね。
講師よくまとまっています。この種の問題では「性能向上」「同じ型なら」のように、もっともらしい理由が添えられた選択肢に注意してください。メモリ確保に限らず、失敗し得る処理は戻り値を確認し、失敗時の処理を必ず書く、と覚えておくと応用が利きます。
まとめ
コーディング規約は、他の人にも読みやすく、不具合が起きにくいコードにそろえるための決まりです。用途の違う変数の使い回しは値の意味を追いにくくし、浮動小数点型のループ制御変数は誤差で反復回数がずれるおそれがあり、性能面の利点もありません。再帰呼出しはスタック使用量を見積もれずスタックオーバーフローの危険があるため、規約で禁止されることもあります。領域割付けの失敗に備えて戻り値を確認し、失敗時の処理を書くことが、規約に定めるべき適切な事項です。
解答・解説
正解はエです
この問題のテーマ
コーディング規約で定めるべき事項を判別する問題です。変数の使い方、ループ制御変数の型、繰り返し処理の書き方、メモリ確保の失敗時の扱いについて、読みやすさと安全性の観点から適切かどうかを考えます。
解き方の考え方
コーディング規約は、コードを読みやすく保ち、不具合を防ぐための決まりです。各選択肢について、「後から読む人が意味を取り違えないか」「実行時に誤差や異常が起きないか」の2点で確かめます。どちらかを損なう書き方を勧めている選択肢は規約として不適切です。
選択肢ごとの解説
- ×ア 局所変数は,用途が異なる場合でもデータ型が同じならば,できるだけ同一の変数を使うようにする。アの、データ型が同じなら用途の違う局所変数を使い回すという記述は不適切です。一つの変数が場所によって別の意味を持つと、読む人が値の意味を追えなくなり、誤用の原因にもなります。変数は用途ごとに分けて定義し、役割の分かる名前を付けるのが原則です。
- ×イ 処理性能を向上させるために,ループの制御変数には浮動小数点型変数を使用する。イの、性能向上のためにループ制御変数を浮動小数点型にするという記述は不適切です。浮動小数点型は加算を繰り返すと誤差がたまり、反復回数が意図とずれることがあります。また、整数型より演算が速いわけでもないため、性能向上の理由にもなりません。制御変数には整数型を使います。
- ×ウ 同様の計算を何度も繰り返すときは,関数の再帰呼出しを用いる。ウの、同様の計算の繰り返しに再帰呼出しを使うという記述は不適切です。再帰呼出しは呼出しの深さによってスタックの使用量が変わり、事前に見積もれないため、スタックオーバーフローを起こすおそれがあります。そのため、規約で再帰を禁止する場合もあります。同じ計算を繰り返すときは、ループを使うか、処理を関数にまとめて呼び出すのが一般的です。
- ○エ 領域割付け関数を使用するときは,割付けができなかったときの処理を記述する。エの、領域割付けに失敗したときの処理を記述するという規定は適切です。メモリの割付けは、空き容量が不足すれば失敗することがあります。失敗に気づかず確保できていない領域を使うと、後続の処理で異常終了などの障害が起きます。戻り値を確認して失敗時の処理を用意することは、規約で定めるべき事項です。
POINT
- コーディング規約の目的は、他の人にも読みやすく、不具合が起きにくいコードにそろえることです。
- 変数は用途ごとに分け、役割の分かる名前を付けます。
- ループ制御変数は整数型にします。浮動小数点型だと誤差がたまり、反復回数がずれることがあります。
- 再帰呼出しはスタック使用量を見積もれないため、規約で制限や禁止をすることがあります。
- メモリ確保などの失敗し得る処理は、戻り値を確認し、失敗時の処理を必ず書きます。
