旧制度の午前・午後と、2023年度以降の科目A・科目Bの公開問題を区別しています。現在の試験対策では現行シラバスと科目Bの形式を確認してください。公開問題は本試験の全出題を網羅する資料ではありません。
2007年度 春期 午後の概要
機械語命令の実行とレジスタ操作
コンピュータシステム · 機械語命令 / レジスタ間演算 / ビットシフト / 論理演算
1語が16ビット(命令部は上位8ビットop、オペランド部はレジスタ指定rが4ビット、レジスタ指定または定数vが4ビット)の機械語について、表に定義された命令(LR: レジスタロード、AR: 加算、OR: 論理和、SL: 左シフト、SR: 右シフト)を実行する。レジスタ1〜5の初期値がレジスタ1: 1234、レジスタ2: 8361、レジスタ3: 5F2A、レジスタ4: C38B、レジスタ5: 0010(いずれも16進数)であるとき、各設問の空欄 a 〜 d に当てはまる数値を求めよ。
- ア
- 【a】9375 / 【b, c】005F / 【d】51
- イ
- 【a】9395 / 【b, c】008B / 【d】52
- ウ
- 【a】9575 / 【b, c】00C3 / 【d】61
- エ
- 【a】9595 / 【b, c】2A00 / 【d】62
- オ
- 【b, c】2A5F
- カ
- 【b, c】8B00
- キ
- 【b, c】8BC3
- ク
- 【b, c】C38B
解答・解説を表示
解答
a: ア, b: カ, c: キ, d: ア
解説
まず要点:機械語命令は「命令の種類」と「対象・値」の部分に分かれ、その指定どおりにCPUがレジスタを操作します。レジスタとは、CPUの中にある高速な一時記憶場所のことです。左シフトは値を2倍・4倍・8倍…にする計算で、これを足し合わせると掛け算を使わずに10倍などの計算ができます。
解き方
- 命令語の上位2桁から命令の種類(LR・AR・OR・SL・SR)を見分け、下位2桁から対象のレジスタ番号と相手の値(レジスタ番号か定数)を読み取ります。
- 設問(1)は、レジスタ2の8361とレジスタ1の1234を2進数に直し、桁ごとの論理和(OR)を計算して9375を求めます。
- 設問(2)は、命令を順番に実行し、レジスタ3がC38B→8B00、レジスタ4が00C3→8BC3と変わっていく様子を追いかけます。
- 設問(3)は、レジスタ5を10倍するため、レジスタ6に8倍を作り、レジスタ5を2倍(1ビット左シフト)にして両者を足す手順を考えます。
小問ごとの答え
- 小問 a:ア
- 命令語3021は、op=30(OR命令)、r=2、v=1を表します。レジスタ2(8361)とレジスタ1(1234)のビットごとの論理和を計算すると、1000 0011 0110 0001 OR 0001 0010 0011 0100 = 1001 0011 0111 0101 となり、16進数で9375となります。
- 小問 b:カ
- 1034によりレジスタ3へレジスタ4の内容(C38B)がコピーされ、続く4038によりレジスタ3が8ビット左シフトされます。空いた下位には0が補われるため、レジスタ3の内容は8B00となります。
- 小問 c:キ
- 5048によりレジスタ4(C38B)が8ビット右シフトされて00C3となり、続く3043によりレジスタ4(00C3)とレジスタ3(8B00)の論理和が計算されてレジスタ4に格納されるため、8BC3となります。
- 小問 d:ア
- 10倍の計算は (x × 8) + (x × 2) = (x << 3) + (x << 1) で実現できます。1065でレジスタ6にレジスタ5を退避し、4063でレジスタ6を3ビット左シフト(8倍)しています。元のレジスタ5を1ビット左シフト(2倍)する必要があるため、命令はSL、対象r=5、シフト量v=1より、オペランドdは51となります。
覚えるポイント
- 論理シフトでは空いたビット位置に常に0が補われる。
- 左nビットシフトは元の値を2のn乗倍することに相当する。
間違えやすいところ
- 16進数の桁ごとの論理和(OR)で、足し算のように繰り上がりが起きると勘違いしてしまう。
- 結果を入れるレジスタと、相手のレジスタ・定数の指定位置を逆に読み取ってしまう。
出題の前提:問題文中に記載された機械語命令の仕様(表1、表2)および初期レジスタ値に基づく。
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.5 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.6 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.7 ↗(cdn.fe-siken.com)
組織情報の関係データベース設計と主キーの検討
データベース · 関係スキーマ設計 / 主キー制約 / 非正規化の弊害 / 多対多の関連
会社の組織と所属社員の情報を管理する関係データベースの設計について、案1(組織: 氏名[PK], 社員番号, 部門名, 部門コード)、案2(組織: 社員番号[PK], 氏名, 部門コード, 部門名)、案3(部門: 部門コード[PK], 部門名 / 社員: 社員番号[PK], 氏名, 部門コード)の比較、および本務に加えて1部門までの兼務を認める制度変更に伴う案4(兼務テーブルの設計)に関して、各空欄に入る適切な選択肢を選べ。
- ア
- 【設問1】転属した社員の所属部門を,変更することができない / 【設問2 c】1 / 【設問2 d, e】氏名
- イ
- 【設問1】新入社員を,登録することができない / 【設問2 c】2 / 【設問2 d, e】社員番号
- ウ
- 【設問1】退職した社員を,削除することができない / 【設問2 c】3 / 【設問2 d, e】部門コード
- エ
- 【設問1】同姓同名の社員を,登録することができない / 【設問2 c】8
- オ
- 【設問1】配属者未定の新設部門を,登録することができない / 【設問2 c】9
解答・解説を表示
解答
設問1 a: オ, 設問1 b: エ, 設問2 c: イ, 設問2 d: イ, 設問2 e: ウ
解説
まず要点:データベースの表は、対象ごとに分けて作ると不整合を防げます。主キー(各行を1つに特定する項目)には重複できない決まりがあるため、同姓同名がありうる「氏名」は主キーに向きません。社員と部門を同じ表にすると、社員がいない新設部門だけを登録できなくなるなどの不便が生じます。
解き方
- 設問1は案1・案2の主キーを確認し、社員側の項目が主キーだと社員がいない部門だけを追加できないことを見つけます。
- 案1では氏名が主キーなので、同姓同名の社員を登録できなくなるという不便に気づきます。
- 設問2は、兼務するのが2名なので兼務表の行数cを2と決めます。
- 兼務は1部門までという決まりから、社員番号で兼務先の部門コードが1つに決まると分かり、主キーdを社員番号、項目eを部門コードと決めます。
小問ごとの答え
- 小問 設問1 a:オ
- 案1・案2ともに1つの表で社員と部門の属性を保持しており、主キーが社員側(氏名または社員番号)にあります。主キーは非空(NOT NULL)である必要があるため、配属者がまだいない新設部門を登録することができません。
- 小問 設問1 b:エ
- 案1では主キーに「氏名」が設定されています。主キーには一意性制約が課されるため、同姓同名の社員が存在する場合に同一の氏名を重複登録することができません。
- 小問 設問2 c:イ
- 問題文より、制度変更および宣伝(SD)の新設に伴って兼務として配属されたのは、綾瀬恵(本務:営業)と上戸満夫(本務:庶務)の2名です。空のレコードは登録しない設計であるため、兼務テーブルの行数は2となります。
- 小問 設問2 d:イ
- 社員は「その他の1部門まで」兼務が可能であるため、1人の社員が持つ兼務先は高々1件です。したがって社員番号によってレコードを一意に特定できるため、主キー d には「社員番号」が入ります。
- 小問 設問2 e:ウ
- 兼務テーブルはどの社員がどの部門を兼務しているかを記録する表です。主キーが社員番号(d)であるため、対応する兼務先の部門を表す属性 e には「部門コード」が入ります。
覚えるポイント
- 主キーにはNOT NULL制約と一意性制約(UNIQUE)が自動的に課される。
- 業務ルール上の多重度(1対多、1対1など)を分析して適切な主キーを決定する。
間違えやすいところ
- 兼務表の主キーを2項目の組み合わせと考えがちですが、兼務は1部門までなので社員番号だけで1行に特定できます。
- 全社員の行を作って兼務なしを空欄で埋める設計と混同しがちですが、問題文では内容が空にならないと決められています。
出題の前提:問題文に提示された組織構造・主キーの定義(図1〜図3)および関係データベースの整合性制約に基づく。
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.8 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.9 ↗(cdn.fe-siken.com)
システム開発の計画立案とアローダイアグラムの分析
プロジェクトマネジメント · アローダイアグラム / クリティカルパス / 所要日数計算 / 工程短縮
あるシステム開発プロジェクトにおいて、ハードウェアの導入とソフトウェアの開発を行う。開発作業の一覧および日程計画のアローダイアグラム(結合点1〜10、作業S1, G1, G2, G3, G4, C1, C2, H1, H2, S2, S3およびダミー作業)に基づき、作業の依存関係、クリティカルパス、最短所要日数、および開発期間短縮のための施策に関する設問に答えよ。
- ア
- 設問1: 業務プログラムの詳細設計(G3)は、共通部品のコーディング・単体テスト(C2)が終了しないと開始できない。 / 設問2 a: ①→②→③→⑤→⑥→⑦→⑧→⑨→⑩ / 設問2 b: 31 / 設問2 c: 共通部品の設計(C1)
- イ
- 設問1: 業務プログラムのコーディング・単体テスト(G4)は、共通部品のコーディング・単体テスト(C2)が終了しないと開始できない。 / 設問2 a: ①→②→③→⑤→⑦→⑧→⑨→⑩ / 設問2 b: 32 / 設問2 c: 共通部品のコーディング・単体テスト(C2)
- ウ
- 設問1: 業務プログラムの詳細設計(G3)は、業務プログラムの機能設計(G2)が終了すると開始できる。 / 設問2 a: ①→②→③→⑥→⑦→⑧→⑨→⑩ / 設問2 b: 33 / 設問2 c: 業務プログラムの機能設計(G2)
- エ
- 設問1: 共通部品は実機がなくてもコーディング・単体テスト(C2)を開始できるが、業務プログラムは実機がなくてはコーディング・単体テスト(G4)を開始できない。 / 設問2 a: ①→②→④→⑨→⑩ / 設問2 b: 34 / 設問2 c: ハードウェアの調達(H1)
- オ
- 設問1: ハードウェアの調達(H1)は、システム方式設計(S1)の完了後に行う。 / 設問2 b: 35
- カ
- 設問2 b: 36
解答・解説を表示
解答
設問1: イ, オ, 設問2 a: ア, 設問2 b: カ, 設問2 c: ア
解説
まず要点:アローダイアグラム(作業の順番と日数を矢印で表した図)では、点に入るすべての作業が終わらないと次へ進めません。全体の日数は、始点から終点までで最も長い経路(クリティカルパス)で決まります。期間を短くするには、その最長経路上の作業を短縮する必要があります。
解き方
- 矢印と点を確認し、どの作業の後にどの作業が来るかの関係をつかみます。
- 始点①から終点⑩までの全経路の日数を計算し、最も長い経路と最短の全体日数を見つけます。
- 全体の短縮につながるのは、最長経路上にある作業だと確認して、当てはまる作業を選びます。
小問ごとの答え
- 小問 設問1:イ, オ
- 作業G4の開始点であるノード⑦にはC2とG3が入るためC2の終了が必要です。またH1はノード②から開始するためS1完了後に行います。
- 小問 設問2 a:ア
- 各経路の日数を比較すると、①→②→③→⑤→⑥→⑦→⑧→⑨→⑩の経路が6+2+6+0+6+6+6+4=36日で最長となりクリティカルパスとなります。
- 小問 設問2 b:カ
- クリティカルパス上の作業日数の合計値が最短所要日数となるため、6+2+6+0+6+6+6+4=36日となります。
- 小問 設問2 c:ア
- 開発全体の期間を短縮するにはクリティカルパス上の作業を短縮する必要があり、選択肢の中でクリティカルパス上にあるのは共通部品の設計(C1)のみです。
覚えるポイント
- クリティカルパスとは所要時間が最長となる経路であり、プロジェクト全体の最短完了日数を決定する。
- 全体の期間短縮はクリティカルパス上の作業を短縮しなければ実現できない。
間違えやすいところ
- 日数0のダミー作業を見落とし、点での作業の合流条件を間違えてしまう。
- 最長経路以外の作業を短縮しても、全体の期間は短くならない点に注意します。
出題の前提:平成19年度春期 基本情報技術者試験 午後 問3
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.10 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.11 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.12 ↗(cdn.fe-siken.com)
挿入ソートのアルゴリズムと計算量
アルゴリズム · 挿入ソート / クイックソート / 計算量 / 整列アルゴリズム
配列A[0]〜A[N]を昇順に整列する挿入ソート(InsertSort)の副プログラムに関する説明と擬似言語プログラムを読み、空欄a〜cを埋めよ。さらに、与えられた配列の例に対する処理の実行回数・条件式変更の影響(空欄d〜f)、およびクイックソートとの計算量に基づく実行時間の比較推定(空欄g)に関する設問に答えよ。
- ア
- 設問1 a: Idx1 / 設問1 b, c: A[Idx2] ← A[Idx2+1] / 設問2 d, e: 2 / 設問2 f: 整列が正しく行われなくなる / 設問3 g: 500
- イ
- 設問1 a: Idx1 + 1 / 設問1 b, c: A[Idx2] ← A[Idx2-1] / 設問2 d, e: 3 / 設問2 f: 整列は正しく行われ,元の条件式の場合と比べて実行ステップ数は多くなる / 設問3 g: 1,000
- ウ
- 設問1 a: Idx1 - 1 / 設問1 b, c: A[Idx2] ← Tmp / 設問2 d, e: 4 / 設問2 f: 整列は正しく行われ,元の条件式の場合と比べて実行ステップ数は変わらない / 設問3 g: 5,000
- エ
- 設問1 b, c: A[Idx2+1] ← A[Idx2] / 設問2 d, e: 19 / 設問2 f: 整列は正しく行われ,元の条件式の場合と比べて実行ステップ数は少なくなる / 設問3 g: 10,000
- オ
- 設問1 b, c: A[Idx2+1] ← Tmp / 設問2 d, e: 20 / 設問3 g: 50,000
- カ
- 設問1 b, c: A[Idx2-1] ← A[Idx2] / 設問2 d, e: 21 / 設問3 g: 500,000
- キ
- 設問1 b, c: A[Idx2-1] ← Tmp
解答・解説を表示
解答
設問1 a: ウ, 設問1 b: エ, 設問1 c: オ, 設問2 d: イ, 設問2 e: カ, 設問2 f: イ, 設問3 g: ウ
解説
まず要点:挿入ソートは、すでに並んだ部分の正しい位置に次の要素を差し込んでいく並べ替え方です。平均の手間はデータ件数の2乗に比例し、逆順のときが最も大変です。クイックソートは件数×log(件数)に比例するため、件数が多いほど挿入ソートより有利になります。
解き方
- 挿入ソートの手順に沿って、ループ変数Idx2の開始値、要素をずらす処理、Tmpを最後に入れる位置の添字を決めます。
- 例1と例2の配列について手作業で処理をたどり、行βが実行される回数を数えます。
- 条件式を>から>=に変えたとき、同じ値の要素がどう扱われるか(ずらしと探索の続行)を考えます。
- n=1,000での実行時間の比から定数の比を求め、n=1,000,000での計算量の比を計算してgを求めます。
小問ごとの答え
- 小問 設問1 a:ウ
- 挿入対象の要素A[Idx1]に対して、比較は直前の要素から手前に向かって行うため、初期値は Idx1 - 1 となります。
- 小問 設問1 b:エ
- Tmpより大きい値を右隣の要素へ移動するため、代入式は A[Idx2+1] ← A[Idx2] となります。
- 小問 設問1 c:オ
- ループ終了時、空いた位置(最後に移動した要素の元の位置または移動がなければIdx1)は Idx2+1 となるため、A[Idx2+1] ← Tmp となります。
- 小問 設問2 d:イ
- 例1 [0, 1, 4, 3, 2, 5, 6] において、行β(シフト処理)は Idx1=3 で1回、Idx1=4 で2回実行され、合計3回となります。
- 小問 設問2 e:カ
- 例2 [6, 5, 4, 3, 2, 1, 0] は完全な逆順のため、行βは各Idx1で 1+2+3+4+5+6 = 21回実行されます。
- 小問 設問2 f:イ
- 条件式を >= にすると同値の要素もシフトするため整列自体は正しく行われますが、余分なシフトと比較が行われるため実行ステップ数は多くなります。
- 小問 設問3 g:ウ
- 計算量の定数比 c2/c1=10 となり、n=1,000,000 では Quick/Insert の比率が 20×(c2/c1)×10^-5 = 2×10^-4 = 1/5,000 となります。
覚えるポイント
- 挿入ソートの平均・最悪計算量は O(n^2)、最良(既に整列済み)計算量は O(n) である。
- クイックソートの平均計算量は O(n log2 n) であり、大量データの整列で圧倒的に高速となる。
間違えやすいところ
- ずらしが終わったときIdx2はすでに1減っているため、実際に入れる位置はIdx2ではなくIdx2+1になるのを見落とす。
- >=を使うと並べ替えが壊れると誤解しがちですが、同じ値どうしの順番が変わるだけで昇順には並びます。
出題の前提:平成19年度春期 基本情報技術者試験 午後 問4
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.13 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.14 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.15 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.16 ↗(cdn.fe-siken.com)
マスタファイルの突合せ更新処理の設計
ソフトウェア設計 · マッチング処理 / マスタ更新 / バッチ処理 / 整列・集約
会員情報マスタファイルと毎月末のトランザクションファイルを用いたマスタ更新プログラムの設計に関する問題である。両ファイルは会員番号で昇順に整列されている。設問1では基本的な突合せループにおけるファイル読み込み(空欄a、b)、設問2では削除処理(更新区分'D')を追加した場合のエラー判定条件(空欄c、d)、設問3では同一会員番号の複数レコードを発生順に処理するための前処理(整列キー e, f、プログラム実行順序 g)について、それぞれ適切なものを解答群から選べ。
- ア
- 設問1: M'入力処理 / 設問2 c: 更新区分 = 'D' / 設問2 d: 更新区分に誤りがある / 設問3 e, f: 会員番号, 発生日時 / 設問3 g: 更新プログラム → 整列プログラム → レコード集約プログラム
- イ
- 設問1: M入力処理 / 設問2 c: 更新区分 = 'U' / 設問2 d: 削除しようとする会員番号をもつレコードがマスタファイルに存在しない / 設問3 e, f: 更新区分 / 設問3 g: 更新プログラム → レコード集約プログラム → 整列プログラム
- ウ
- 設問1: T入力処理 / 設問2 c: 更新区分 ≠ 'D' / 設問2 d: 新規登録しようとする会員番号をもつレコードがマスタファイルに存在する / 設問3 e, f: サービス等級 / 設問3 g: 整列プログラム → 更新プログラム → レコード集約プログラム
- エ
- 設問2 c: 更新区分 ≠ 'U' / 設問2 d: 変更しようとする会員番号をもつレコードがマスタファイルに存在しない / 設問3 e, f: 発生日時 / 設問3 g: 整列プログラム → レコード集約プログラム → 更新プログラム
- オ
- 設問2 c: (更新区分 ≠ 'D') AND (更新区分 ≠ 'U') / 設問3 g: レコード集約プログラム → 更新プログラム → 整列プログラム
- カ
- 設問2 c: (更新区分 ≠ 'D') OR (更新区分 ≠ 'U') / 設問3 g: レコード集約プログラム → 整列プログラム → 更新プログラム
解答・解説を表示
解答
設問1 a: イ, 設問1 b: ウ, 設問2 c: オ, 設問2 d: イ, 設問3 e: ア, 設問3 f: エ, 設問3 g: エ
解説
まず要点:2つのファイルを突き合わせる処理では、両方を同じキーの昇順に並べておき、キーの大小を見てどちらを先に進めるかを決めます。並んでいなかったり同じキーが複数あったりする場合は、先に並べ替えとまとめ(集約)をして1対1の形に整えます。
解き方
- 図1の条件に従い、KM<KTならMだけを進め(M入力処理)、KM>KTならTだけを進める(T入力処理)ことを見つけます。
- 図2の分岐で、正しい値('U'と'D')以外を見つける条件X2を論理式で表します。
- 削除処理でKM>KT(マスタ側のキーが大きく、対象のキーがマスタに無いまま追い越された)状態が、マスタに存在しないエラーだと確認します。
- 同じ会員の複数の取引を起きた順にまとめるため、並べ替えのキー(会員番号→発生日時)と実行の順番(整列→集約→更新)を決めます。
小問ごとの答え
- 小問 設問1 a:イ
- KM < KT の分岐では、マスタレコードMに対応するトランザクションTが存在しないため、Mを新マスタへ出力した後に次のマスタレコードを読み込む必要があるため「M入力処理」を行う。
- 小問 設問1 b:ウ
- KM > KT の分岐では、トランザクションTに対応するマスタレコードが存在しない新規追加である。Tを新マスタへ出力した後は次のトランザクションを読み込むため「T入力処理」を行う。
- 小問 設問2 c:オ
- 更新区分は新規登録・変更を表す'U'か、削除を表す'D'のいずれかでなければならない。エラー処理1に進む条件X2は、不正な区分値である場合なので「(更新区分 ≠ 'D') AND (更新区分 ≠ 'U')」となる。
- 小問 設問2 d:イ
- 条件X3は更新区分が'D'(削除)の場合であり、その後のKM:KTの判定でKM > KTの枝は、削除対象のレコードがマスタファイルに存在しないことを意味する。したがってエラー処理2は「削除しようとする会員番号をもつレコードがマスタファイルに存在しない」場合に実行される。
- 小問 設問3 e:ア
- レコード集約プログラムで同一会員番号のレコードをまとめるため、整列プログラムでは第1整列キーを「会員番号」とする。
- 小問 設問3 f:エ
- 同一会員番号の中で発生順に処理するため、第2整列キーを「発生日時」とする。
- 小問 設問3 g:エ
- トランザクションファイルをまず「整列プログラム」で会員番号昇順・発生日時昇順に並べ替え、次に「レコード集約プログラム」で1会員1レコードに集約し、最後にその集約ファイルを入力として「更新プログラム」を実行する。
覚えるポイント
- 順ファイルのマッチングはキーの大小関係に応じた片送り・両送りの制御が基本である。
- 集約処理を行う前には、キーごとにグループ化されるよう整列(ソート)を先行させる。
間違えやすいところ
- 設問2 cで「'D'でも'U'でもない」という条件をORでつないでしまい、すべてのレコードがエラーになる誤りです。
- 設問3 gで更新処理を先に動かしてしまい、複数のレコードを起きた順に処理できなくなる誤りです。
出題の前提:基本情報技術者試験 午後 問5 共通出題基準
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.17 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.18 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.19 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.20 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.21 ↗(cdn.fe-siken.com)
C言語による双六ゲームの制御プログラム
個別ソフトウェア開発(C言語) · C言語 / テーブルドリブン / 配列・ループ制御 / switch文
4人のプレーヤがさいころ2個を振ってコース上を進む双六(すごろく)ゲームのC言語プログラムに関する問題である。コースの各升(0〜23)の動作指示はactype配列およびcelinf配列に定義されている(テーブルドリブン方式)。設問1では、升の指示による移動・休みの継続判定条件(空欄a)、ゲーム終了判定条件(空欄b)、次のプレーヤへの手番交代処理(空欄c)を埋めよ。設問2では、新たに「続けてさいころを振り、駒を進める」動作指示(actype=3)を追加する場合の処理(空欄d)を解答群から選べ。
- ア
- 設問1 a: actype[curpos[playerid]] != 0 / 設問1 c: playerid = playerid % PLAYERS + 1 / 設問2 d: curpos[playerid] = celinf[curpos[playerid]]
- イ
- 設問1 a: actype[curpos[playerid]] <= 3 / 設問1 c: playerid = playerid % (PLAYERS + 1) / 設問2 d: curpos[playerid] = celinf[curpos[playerid]] + dice(playerid)
- ウ
- 設問1 a: curpos[playerid] == 0 / 設問1 c: playerid = (playerid + 1) % PLAYERS / 設問2 d: curpos[playerid] += celinf[curpos[playerid]] + dice(playerid)
- エ
- 設問1 b: curpos[playerid] >= CELLS - 1 / 設問1 c: playerid += 1 / 設問2 d: curpos[playerid] += dice(playerid)
- オ
- 設問1 b: gamestatus == 0 / 設問1 c: playerid += playerid / (PLAYERS - 1) / 設問2 d: playmode[playerid] = PLAY
- カ
- 設問1 b: gamestatus == 1
- キ
- 設問1 b: playmode[playerid] == PLAY
- ク
- 設問1 b: playmode[playerid] == WAIT
解答・解説を表示
解答
設問1 a: ア, 設問1 b: エ, 設問1 c: ウ, 設問2 d: エ
解説
まず要点:テーブルドリブン方式では、細かい条件分岐を並べずに、状態や動作の種類を表(配列)に入れて制御します。また、順番を0→1→2→…→0と一巡させるには、(i+1)%Nのような割り算の余りの計算を使うと簡単に書けます。
解き方
- while文で、現在位置のactypeが0(指示なし)でない間くり返すように、空欄aを決めます。
- マスの番号が上がりのマス(CELLS-1=23)以上になったら終了とするように、空欄bを決めます。
- プレーヤID(0,1,2,3)を順に一巡させる式(playerid+1)%PLAYERSを空欄cに選びます。
- 「続けてさいころを振って進む」という指示は、dice関数の値を現在位置curposに足す処理なので、空欄dを決めます。
小問ごとの答え
- 小問 設問1 a:ア
- 移動先の升にさらに指示がある限り繰り返すため、指示が存在することを示す条件「actype[curpos[playerid]] != 0」が入る。
- 小問 設問1 b:エ
- 上がりの升(番号23)に到達またはそれを超えたときに勝ちとなりゲーム終了(gamestatus = 0)とするため、「curpos[playerid] >= CELLS - 1」が入る。
- 小問 設問1 c:ウ
- 4人のプレーヤ(0〜3)の手番を巡回させるため、剰余算を用いて「playerid = (playerid + 1) % PLAYERS」とする。
- 小問 設問2 d:エ
- 「続けてさいころを振り、駒を進める」動作なので、現在の位置にさいころの目の和を加算する「curpos[playerid] += dice(playerid)」が入る。
覚えるポイント
- 要素数Nの環状ループインデックス更新は (index + 1) % N で行う。
- テーブルドリブン方式ではデータの値(コード)に応じてswitch等で処理を振り分ける。
間違えやすいところ
- 設問1 cでplayerid = playerid % PLAYERS + 1を選ぶと1〜4になり、配列の範囲外アクセスを起こす誤りです。
- 設問2 dで、指定マスへ飛ぶ処理(celinfの加算)とさいころを振る処理を混同してしまう誤りです。
出題の前提:基本情報技術者試験 午後 問6 共通出題基準
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.22 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.23 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.24 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.25 ↗(cdn.fe-siken.com)
選挙速報集計プログラムの表操作とテストデータ
ソフトウェア開発(COBOL) · COBOL / SEARCH文 / 内部表の操作 / 整列アルゴリズム / 命令網羅テスト
地区ごとの開票情報を読み込み、候補者ごとの得票数を集計して得票数の降順に表示するCOBOLプログラムに関する問題である。プログラム中の空欄 a 〜 c に入る適切な字句、およびプログラムのすべての命令を実行する命令網羅テストに適した開票ファイルの入力データを選択せよ。
- 設問1 a ア
- ADD K-TOKUHYO-SU TO S-TOKUHYO-SU(S-IDX)
- 設問1 a イ
- ADD K-TOKUHYO-SU TO S-TOKUHYO-SU(S-MAX)
- 設問1 a ウ
- MOVE K-TOKUHYO-SU TO S-TOKUHYO-SU(S-MAX)
- 設問1 a エ
- MOVE S-TBL(W-I) TO S-TBL(W-J)
- 設問1 a オ
- MOVE S-TBL(W-J) TO S-TBL(W-I)
- 設問1 b ア
- ADD K-TOKUHYO-SU TO S-TOKUHYO-SU(S-IDX)
- 設問1 b イ
- ADD K-TOKUHYO-SU TO S-TOKUHYO-SU(S-MAX)
- 設問1 b ウ
- MOVE K-TOKUHYO-SU TO S-TOKUHYO-SU(S-MAX)
- 設問1 b エ
- MOVE S-TBL(W-I) TO S-TBL(W-J)
- 設問1 b オ
- MOVE S-TBL(W-J) TO S-TBL(W-I)
- 設問1 c ア
- ADD K-TOKUHYO-SU TO S-TOKUHYO-SU(S-IDX)
- 設問1 c イ
- ADD K-TOKUHYO-SU TO S-TOKUHYO-SU(S-MAX)
- 設問1 c ウ
- MOVE K-TOKUHYO-SU TO S-TOKUHYO-SU(S-MAX)
- 設問1 c エ
- MOVE S-TBL(W-I) TO S-TBL(W-J)
- 設問1 c オ
- MOVE S-TBL(W-J) TO S-TBL(W-I)
- 設問2 ア
- 候補者名WWWWWW, XXXXXX, XXXXXX, ZZZZZZ, VVVVVV, WWWWWWの順(昇順・降順の両方が生じない)
- 設問2 イ
- すべてのレコードの候補者名がUUUUUU(候補者が1人のみ)
- 設問2 ウ
- 同一候補者の連続がなく、得票数の比較で交換が発生しない(降順ソート済みの得票数)
- 設問2 エ
- すべて異なる候補者で重複がなく、同一候補者への加算が行われない
- 設問2 オ
- 同一候補者の再登場(加算処理の実行)と、整列処理で値の交換(IF文が真)の両方を網羅するデータ
解答・解説を表示
解答
設問1 a: ウ, 設問1 b: ア, 設問1 c: オ, 設問2: オ
解説
まず要点:COBOLのSEARCH文は表を先頭から順に探し、見つかればWHEN句、見つからなければAT END句を実行します。並べ替えの入れ替えには、一時的な場所を使って2つの値を交換する手順が必要です。命令網羅テストでは、すべての命令が1回以上実行されるような入力データを用意します。
解き方
- 集計処理(SHUKEI-PROC)で、新規追加(AT END句)と既存加算(WHEN句)の操作を見分け、空欄aとbを決めます。
- 整列・表示処理(SHUKEI-DISP)の交換の手順で、代入の順番から空欄cを決めます。
- 新規登録・既存加算・並べ替え交換をすべて実行する条件を満たすよう、入力データの候補者名と票数の動きを確かめます。
小問ごとの答え
- 小問 設問1 a:ウ
- SEARCH文のAT END句は候補者がまだ表に存在しない場合に実行される。このときS-MAXに1を加算して新たな候補者領域を作成し、候補者名を設定した直後であるため、その要素S-MAXの得票数に初回レコードの得票数K-TOKUHYO-SUを代入(MOVE)する。
- 小問 設問1 b:ア
- WHEN条件が成立したときは、既存の候補者名と一致した位置を指標S-IDXが指している。したがって、その要素S-IDXの既存の得票数に入力レコードの得票数を加算(ADD K-TOKUHYO-SU TO S-TOKUHYO-SU(S-IDX))する。
- 小問 設問1 c:オ
- SHUKEI-DISPでの選択ソートにおいて、S-TOKUHYO-SU(W-I) < S-TOKUHYO-SU(W-J)のときに要素W-Iと要素W-Jを入れ替える。退避領域W-TBLにS-TBL(W-I)を代入後、空いたS-TBL(W-I)にS-TBL(W-J)を代入し、最後にS-TBL(W-J)にW-TBLを代入する。
- 小問 設問2:オ
- 命令網羅では、新規候補者追加(AT END句)、既存候補者への加算(WHEN句)、およびソート時の値入れ替え処理(IF文の真ルート)のすべての文が最低1回実行される必要がある。選択肢オのデータは、同じ候補者XXXXXXとWWWWWWが複数回出現してWHEN句を通り、かつ初期の合計得票順が降順になっていないためIF文の真ルート(要素の交換)も通過する。
覚えるポイント
- COBOLのSEARCH文では一致時にWHEN句、不一致で表終了時にAT END句が実行される。
- 命令網羅テストではプログラム内に存在するすべての文(命令)が1回以上実行される入力を選択する。
間違えやすいところ
- AT END句で新しいレコードの票数を足し算(ADD)と誤解し、まだ値のない場所に足してしまう。
- 交換処理で退避する側と代入する側の順番を逆にし、同じデータを二重に上書きしてしまう。
出題の前提:平成19年度春期基本情報技術者試験午後問7
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.26 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.27 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.28 ↗(cdn.fe-siken.com)
JavaのComparatorインタフェースとジェネリクス
ソフトウェア開発(Java) · Java / Comparator / Generics / Arrays.sort / Map / 辞書順と数値順ソート
英語の月名(January〜December)を辞書順および月のカレンダー順に並べ替えるJavaプログラムに関する問題である。プログラム中の空欄 a 〜 d に入る適切な字句を選択せよ。
- a ア
- Comparator<int>
- a イ
- Comparator<Integer>
- a ウ
- Comparator<Object>
- a エ
- Comparator<String>
- b ア
- i < monthNames.length
- b イ
- i <= monthNames.length
- b ウ
- i > monthNames.length
- b エ
- i >= monthNames.length
- c ア
- map.get(ls1) + map.get(ls2)
- c イ
- map.get(ls1) - map.get(ls2)
- c ウ
- map.get(ls1) / map.get(ls2)
- c エ
- map.get(ls2) - map.get(ls1)
- d ア
- new Comparator()
- d イ
- new Comparator<String>()
- d ウ
- new ValueComparator()
- d エ
- new ValueComparator<String>()
解答・解説を表示
解答
a: エ, b: ア, c: イ, d: ウ
解説
まず要点:JavaのComparatorは、2つのものを比べる「基準」を決めるための仕組み(インタフェース)です。compareメソッドは、1つ目が小さければ負、等しければ0、大きければ正の数を返すように作ります。総称型(<>の中)には、intのような基本型ではなく参照型を指定します。
解き方
- 空欄a:並べ替える対象がStringの配列で、compareの引数もStringなので、Comparator<String>を実装すると分かります。
- 空欄b:monthNamesの全要素(0〜length-1)をたどるforループの条件i < monthNames.lengthを選びます。
- 空欄c:昇順に並べるため、1つ目の月番号から2つ目の月番号を引く式map.get(ls1)-map.get(ls2)を選びます。
- 空欄d:月の順に並べ替えるため、ValueComparatorをそのままnewで実体化する式を選びます。
小問ごとの答え
- 小問 a:エ
- ValueComparatorクラスはString型の配列要素を比較するため、ジェネリクス型引数としてStringを指定したComparator<String>を実装(implements)する。
- 小問 b:ア
- 配列monthNamesのインデックスは0からlength - 1までであるため、ループの継続条件はi < monthNames.lengthとする。
- 小問 c:イ
- Comparatorのcompareメソッドは、第1引数が第2引数より小さいときに負、等しいときに0、大きいときに正を返す昇順比較を行うため、map.get(ls1) - map.get(ls2)とする。
- 小問 d:ウ
- カレンダーの月の順にソートするためにはValueComparatorのインスタンスを生成して渡す。ValueComparatorクラス自体は総称型クラスとして定義されていないため、型引数を付けずにnew ValueComparator()とする。
覚えるポイント
- Comparatorのcompare(o1, o2)は、昇順ならo1 - o2、降順ならo2 - o1の符号を返すように設計する。
- ジェネリクス(総称型)の型パラメータにはプリミティブ型を指定できず、参照型を指定する。
間違えやすいところ
- <>の中にintのような基本データ型を指定してしまう誤りです。
- compareメソッドで、昇順にするための引き算の順番(o1-o2とo2-o1)を逆にしてしまう誤りです。
出題の前提:平成19年度春期基本情報技術者試験午後問8
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.29 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.30 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.31 ↗(cdn.fe-siken.com)
ビット列の左右対称性検査プログラム(CASL II)
ソフトウェア · CASL II / ビット演算 / シフト命令 / 条件分岐
16ビットからなるビット列が左右対称であるかどうかを検査する副プログラムSYMTSTに関する問題である。ビット列はGR1に渡され、左右対称であればGR0に1を、そうでなければ0を設定して主プログラムへ復帰する。プログラム中の空欄を埋め、指定された入力データに対するレジスタ内容や命令実行回数を求める。
解答・解説を表示
解答
設問1 a: エ, 設問1 b: オ, 設問2: イ, 設問3: ウ
解説
まず要点:左右対称かどうかは、左端と右端のビットを1つずつ取り出して比べれば判定できます。左シフトで左端のビットを、右シフトで右端のビットを、それぞれ溢れフラグ(はみ出したビットを覚えておく目印)へ送り出します。そして両方が同じ値(ともに1か、ともに0)かどうかを順に照合していきます。
解き方
- GR1を左に、GR2を右にそれぞれシフトして、左端と右端のビットをOFに取り出し、両者が一致するか調べる手順をつかむ。
- カウンタGR3を減らした結果で分岐する命令(JPL)と、一致・不一致のときの処理の流れを押さえ、与えられたビット列での動きを追いかける。
小問ごとの答え
- 小問 設問1 a:エ
- 行5のSLL命令で最上位ビット(MSB)が1のとき、OF=1となって行10のOFLOWへ分岐します。OFLOWではGR2をSRL(論理右シフト)して最下位ビット(LSB)をOFへ追い出します。左右対称であるためにはLSBも1でなければならないため、OF=1のときに一致と判断してOKへ分岐する「JOV OK」が入ります。OF=0の場合は不一致なので行12のNGへそのまま進みます。選択肢ア(JMI LOOP)、イ(JOV NG)、ウ(JOV OFLOW)、オ(JPL LOOP)、カ(JZE LOOP)はいずれも不適切です。
- 小問 設問1 b:オ
- 左右のビットが一致したときはOK(行14)に進み、ループカウンタGR3から1を減じます(SUBA GR3,=1)。初期値8から1ずつ減算され、1〜7回目の減算結果は正数となるため、次のビット検査を行うべく「JPL LOOP」でループ先頭へ戻ります。8回目の減算でGR3が0になると正数ではなくなるため分岐せず、行16に進んでGR0に1を設定します。選択肢ア(JMI LOOP)、イ(JOV NG)、ウ(JOV OFLOW)、エ(JOV OK)、カ(JZE LOOP)はループ継続条件として不適です。
- 小問 設問2:イ
- 与えられたビット列「10110101 10101101」は左右対称です。8回のループ処理ですべてビットが一致し、行16でGR0に1が設定された後、行17のRPOP直前に至ります。ループ1回ごとにGR2はSRL(論理右シフト)で1ビットずつ右シフトされるため、合計8回右シフトされます。論理右シフトでは上位に0が補填されるため、元のビット列の上位8ビット(10110101)が下位8ビットへ移動し、上位8ビットは「00000000」となります。したがってGR2の内容は「00000000 10110101」となります。
- 小問 設問3:ウ
- ビット列「10110101 10100101」について各ビットの検査を追跡します。行10のSRL命令はSLL GR1,1の実行結果でOF=1となったとき(すなわちGR1の左端ビットが1のとき)に実行されます。1ビット目は1なのでOFLOWへ分岐し実行(1回目)。2ビット目は0なので行7を実行。3ビット目は1なのでOFLOWへ分岐し実行(2回目)。4ビット目は1なのでOFLOWへ分岐し実行(3回目)。このときGR2の右端ビットは0なのでOF=0となり、行11で分岐せず行12のNGへ進んで終了します。したがって行10のSRL命令は合計3回実行されます。
覚えるポイント
- CASL IIの論理シフト命令(SLL/SRL)では、最後に押し出されたビットがフラグOFに設定され、空いたビットには0が入る。
- JPL命令はフラグSF=0かつZF=0(結果が正)のときに分岐し、結果が0のときは分岐しない。
間違えやすいところ
- 引き算の直後に「0でない」判定のJNZを選ぶと、GR3が負でもループが続いてしまうので、終了判定にはJPLを使う。
- 論理右シフト(SRL)を8回行ったあと、レジスタの上のほうには1ではなく0が詰まる点を見落としやすい。
出題の前提:平成19年度春期基本情報技術者試験 午後 問9(アセンブラ言語 CASL II)
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.32 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.33 ↗(cdn.fe-siken.com)
リーグ戦の勝敗表と順位表の出力プログラム(C言語)
ソフトウェア · C言語 / 構造体 / ポインタ配列 / 型変換(キャスト) / ソート
リーグ戦の勝敗表から勝率を計算し、勝率の高い順に順位を付与して出力するC言語プログラムに関する問題である。構造体配列teamの各要素へのポインタを配列pTeamに格納して整列を行い、同率順位を考慮した順位付けを行って結果を表示する。
解答・解説を表示
解答
設問1 a: エ, 設問1 b: ウ, 設問2 c: ア, 設問2 d: ウ, 設問2 e: ウ
解説
まず要点:構造体そのものを並べ替えると、大きなデータのコピーが何度も起きて遅くなります。そこで、構造体へのポインタ(データの在りかを指す番号)を配列に入れ、ポインタの順番だけを並べ替えれば、動かすデータを小さくできて効率的です。
解き方
- calcAverage関数で、整数どうしの割り算にならないよう型を変換することと、0で割らないための条件分岐を正しく書く。
- ポインタ配列pTeamに各構造体のアドレスを入れ、並べ替えたあとの配列からアロー演算子で中身を参照し、順位を付けて出力する流れを読む。
小問ごとの答え
- 小問 設問1 a:エ
- 関数の仕様として「試合数が0の場合、勝率は0.0とする」と規定されています。試合数は勝ち数と負け数の和であるtotal(team[i].wins + team[i].losses)に格納されるため、勝率を0.0とする条件式は「total == 0」となります。選択肢アおよびイは計算前の平均値による判定、ウはゼロ除算を招く逆の条件であり不適です。
- 小問 設問1 b:ウ
- 勝率は「勝ち数 / 試合数」で計算します。winsおよびtotalはともにint型であるため、そのまま整数同士で除算すると小数点以下が切り捨てられます。double型の値を得るには被除数を「(double)team[i].wins」のように明示的にキャストして除算を行う必要があります。選択肢アは左辺をキャストしており構文エラー、イは除算後にキャストしているため切り捨て後の整数となり、エは整数除算となるため誤りです。
- 小問 設問2 c:ア
- 処理手順(2)に「配列teamの各要素のアドレスを、先頭要素から順番に配列pTeamの各要素に格納する」とあります。team[i]のアドレスは「&team[i]」で取得でき、ポインタ配列のi番目の要素pTeam[i]に代入するため「pTeam[i] = &team[i]」が正解です。選択肢イは型不一致、ウおよびエは構造体そのものの代入を意図しておりポインタ配列の初期化として不適です。
- 小問 設問2 d:ウ
- 勝率が同率の場合は同順位とし、勝率が変わったときはそのチームの並び順に応じた順位(1始まり)を付与します。図2の出力例では、2チームが同率3位となった次の5チーム目の順位は4位ではなく「5位」となっています。配列のインデックスiは0から始まるため、勝率が前チームと異なる場合の順位は「rank = i + 1」によって更新されます。選択肢アのrank++では4位になってしまい、イ・エ・オの計算式も出力仕様を満たしません。
- 小問 設問2 e:ウ
- 整列処理sort(pTeam)によって、勝率降順にポインタ配列pTeamの要素が並び替えられています。出力ループではi番目のチームの情報を参照して表示するため、RECORD構造体を指すポインタ「pTeam[i]」を用いて「pTeam[i]->name」「pTeam[i]->wins」のようにアロー演算子でメンバにアクセスします。選択肢アは未ソートのteam配列を参照しており、イおよびエはrankを用いた不適切な参照です。
覚えるポイント
- int型同士の除算は商の整数部分のみとなるため、実数計算を行うには少なくとも一方をdouble型にキャストする。
- 同率順位においてタイが生じた直後の順位は「直前の順位+1」ではなく「それまでの累積人数+1(すなわち現在のインデックス+1)」となる。
間違えやすいところ
- (double)(wins / total)のように割り算全体を変換しても、括弧の中の整数の割り算ですでに小数が切り捨てられている点に注意。
- 同着の順位をrank++で更新すると、同率のあとの順位の飛び(3位が2人なら次は5位)が表せない。
出題の前提:平成19年度春期基本情報技術者試験 午後 問10(C言語)
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.34 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.35 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.36 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.37 ↗(cdn.fe-siken.com)
COBOLプログラムによる保護者名簿ファイルの突合せ更新処理
ソフトウェア開発 · COBOL / マッチング処理 / 順ファイル更新 / 条件判定
小学校の昨年度の保護者名簿ファイルと新入学生の保護者名簿ファイルを突合せ処理し、本年度の保護者名簿ファイルを新規作成するCOBOLプログラムに関する問題である。昨年度名簿と新入学名簿はともに保護者氏名および電話番号(ID)の昇順に整列されている。在校児童の学年を1年繰り上げ、6年生修了者は卒業として除外し、新1年生を追加する。児童が全員卒業して新入生のいない世帯の保護者レコードは削除する。プログラム中の空欄 a〜d に当てはまる字句、および削除対象となった保護者情報を画面表示するための適切な変更箇所を解答せよ。
- ア
- 設問1 a: NOT (OLD-EOF AND ENT-EOF) / 設問1 b〜d: ADD 1 TO OLD-NUM(OLD-CNT) / 設問2: 行番号53と54の間に追加
- イ
- 設問1 a: NOT (OLD-EOF OR ENT-EOF) / 設問1 b〜d: MOVE OLD-ID TO NEW-ID / 設問2: 行番号82と83の間に追加
- ウ
- 設問1 a: OLD-EOF AND ENT-EOF / 設問1 b〜d: MOVE OLD-PUPIL(ENT-CNT) TO NEW-PUPIL(NEW-CNT) / 設問2: 行番号90と91の間に追加
- エ
- 設問1 a: OLD-EOF OR ENT-EOF / 設問1 b〜d: MOVE OLD-PUPIL(OLD-CNT) TO NEW-PUPIL(NEW-CNT) / 設問2: 行番号92と93の間に追加
- オ
- 設問1 b〜d: MOVE W-OLD-REC TO W-NEW-REC
- カ
- 設問1 b〜d: PERFORM ENT-ADD-PROC
解答・解説を表示
解答
設問1 a: ア, 設問1 b: オ, 設問1 c: エ, 設問1 d: ア, 設問2: イ
解説
まず要点:突合せ処理では、2つのファイルのキーを比べて「片方にだけある」「両方にある」を場合分けして処理します。ここでは在校生の学年を1つ上げ、6年生は卒業として外し、新1年生を加えます。そして児童が1人もいなくなった世帯のレコードは削除し、その検出方法を考えます。
解き方
- 主処理の繰り返しの仕組みと、ファイルの読み込みが終わったかを見る条件を調べ、aに入る式を導く。
- キー(OLD-IDとENT-ID)の比較で分かれる3つの場合(旧のみ・両方一致・新のみ)の役割を確かめ、bとcのデータ移動命令を決める。
- 学年を1つ上げる副処理NUM-UP-PROCの中身を確かめ、進級のときに数を足す処理dを特定する。
- 保護者の記録が出されず消される条件(在校生が全員卒業し、新入生もいない)を判断する場所を探し、削除を表示する命令の入れどころを決める。
小問ごとの答え
- 小問 設問1 a:ア
- メインループは行41のPERFORM UNTIL OLD-EOF AND ENT-EOFで両ファイルが終了するまで繰り返されます。行52のIF a THEN PERFORM CREATE-PROCでは、両方のファイルが同時に終了していない(少なくとも一方に未処理レコードが残っている)間に処理を実行する必要があるため、NOT (OLD-EOF AND ENT-EOF)が適切です。
- 小問 設問1 b:オ
- OLD-ID < ENT-IDの条件は、昨年度名簿にのみ存在する保護者の処理です。NUM-UP-PROCで学年繰上げ処理を行った後、新年度名簿用の作業領域へ転記する必要があるため、MOVE W-OLD-REC TO W-NEW-RECを実行します。
- 小問 設問1 c:エ
- OLD-ID = ENT-IDの場合、新入学児童(学年1)がENT-ADD-PROCによりNEW-PUPIL配列の先頭側に格納されます。その後、繰り上がった既存の在校児童を空きスロットに転記するため、MOVE OLD-PUPIL(OLD-CNT) TO NEW-PUPIL(NEW-CNT)を実行します。
- 小問 設問1 d:ア
- 学年繰上げ処理NUM-UP-PROCにおいて、学年が6未満(OLD-NUM(OLD-CNT) < 6)の児童は進級するため、学年を1加算するADD 1 TO OLD-NUM(OLD-CNT)を実行します。
- 小問 設問2:イ
- CREATE-PROCの行81〜83では、NEW-PUPIL(1) NOT = SPACEであれば児童が存在するため新名簿に出力(WRITE)しています。児童が全員卒業してNEW-PUPIL(1)が空白のままの世帯は削除対象となるため、行82のWRITEの後にELSE節を設けてDISPLAY文を追加するイが正しいです。
覚えるポイント
- 順ファイル突合せでは両方EOFになるまで読込みを継続し、未終了側の処理を最後まで流す
- OCCURSで定義された配列要素の操作時は、ポインタやカウンタ変数の対応関係に注意する
間違えやすいところ
- ループを終える条件(UNTIL A AND B)と、ループの中で処理を行う条件(NOT (A AND B))を逆にしてしまう間違い。
- 新入生を加えたあとの旧児童の複写で、取り出し元の添字にNEW-CNTやENT-CNTを使ってしまう間違い。
出題の前提:平成19年度春期基本情報技術者試験午後問11の出題条件に基づく
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.38 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.39 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.40 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.41 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.42 ↗(cdn.fe-siken.com)
Javaプログラムによる三目並べの盤面管理と取り消し(undo)機能の実装
ソフトウェア開発 · Java / 列挙型(enum) / 盤面探索アルゴリズム / 例外処理
3×3の升目で先手(○:CIRCLE)と後手(×:CROSS)が交互に記号を配置する三目並べ(Tic-Tac-Toe)のJavaプログラムに関する問題である。盤面の状態(進行中、先手勝ち、後手勝ち、引き分け)や着手可否の例外送出、縦・横・斜めの揃い判定、直前の着手を取り消すundoメソッドの仕様について、プログラム中の空欄 a〜d を埋め、undoメソッドの動作に関する正しい記述を解答群から2つ選べ。
- ア
- 設問1 a: Mark.BLANK / 設問1 b: count < 0 / 設問1 c: -1, -1 / 設問1 d: i / 設問2: 2手目以降で続けて2回呼ぶと、二つ消せる。
- イ
- 設問1 a: Mark.CIRCLE / 設問1 b: count >= 9 / 設問1 c: -1, 1 / 設問1 d: i % 2 / 設問2: 2手目以降で続けて2回呼ぶと、呼ばなかった状態に戻る。
- ウ
- 設問1 a: Mark.CROSS / 設問1 b: progress != Progress.IN_PROGRESS / 設問1 c: 1, -1 / 設問1 d: i & 2 / 設問2: 2手目以降で続けて2回呼んでも、消せるのは一つだけである。
- エ
- 設問1 a: null / 設問1 b: progress == Progress.IN_PROGRESS / 設問1 c: 1, 1 / 設問1 d: i / 2 / 設問2: ゲーム中で先手後手とも、それぞれ1回しか消せない。
- オ
- 設問2: 消すことができなければ例外を投げる。
解答・解説を表示
解答
設問1 a: ア, 設問1 b: ウ, 設問1 c: ウ, 設問1 d: イ, 設問2: ウ, オ
解説
まず要点:三目並べの勝敗は、最後に置いたマスを通る縦・横・斜めに同じ印がそろうかで判定します。増分(dx, dy)を使う同じ関数checkで4方向をまとめて調べられます。また取り消し(undo)では、最後の1手を消して手番と着手数を戻し、消せないときは例外を出す管理が大切です。
解き方
- 盤面すべてのマスの初期値と、勝負がついたか(進行中でないか)を調べる条件式を確かめ、aとbを導く。
- 3マスの座標を決める式(x + k*dx, y + k*dy)を使い、右上(0, 2)から左下(2, 0)へ向かう斜めを調べる増分cを計算する。
- テスト用クラスで、偶数手と奇数手で先手・後手の印を切り替えるための添字の式dを求める。
- undoメソッドの中身を順に追い、直前の1手しか覚えていないことによる制限と、例外を出す条件を調べて設問2の記述を選ぶ。
小問ごとの答え
- 小問 設問1 a:ア
- コンストラクタ内で3×3の盤面全要素を初期化しています。問題文の説明により「升に何も書かれていない状態をMark.BLANKで表す」と定められているため、Mark.BLANKを設定します。
- 小問 設問1 b:ウ
- putメソッドの仕様で「既に勝敗が決まっているとき(引き分けを含む)は IllegalStateException を投げる」とあります。ゲームが進行中ではない状態を示す条件式は progress != Progress.IN_PROGRESS です。
- 小問 設問1 c:ウ
- 右上から左下への斜めの列を検査するcheck(0, 2, dx, dy, mark)の呼び出しです。開始升が(0, 2)なので、次は(1, 1)、その次は(2, 0)とxが+1、yが-1ずつ変化するため、増分(dx, dy)は(1, -1)となります。
- 小問 設問1 d:イ
- テストプログラムTicTesterにおいて、先手CIRCLEと後手CROSSを交互に切り替えるため、インデックスiを2で割った余りである i % 2 を用いて配列marksから手番の記号を取得します。
- 小問 設問2:ウ, オ
- undo()メソッドは直前の1手分の座標(lastx, lasty)しか保持しておらず、一度実行するとその升はMark.BLANKになります。続けて2回目のundo()を呼ぶと、board[lastx][lasty] != Mark.BLANKの条件が偽となりIllegalStateExceptionが投げられます。したがって消せるのは1つだけであり(ウ)、消せない場合は例外を投げます(オ)。
覚えるポイント
- 方向ベクトルを用いたグリッド探索では、(開始点x, 開始点y, dx, dy)の組み合わせで全方向を同一ロジックで走査できる
- 履歴保持変数が単一の変数(lastx, lasty)の場合、スタック構造を持たない限り連続した複数手のundoは実現できない
間違えやすいところ
- 斜めの増分で、(dx, dy)の符号を逆にして(-1, 1)や(-1, -1)と間違えること。
- undoを続けて呼ぶと手番が戻るので2手前も消せると誤解すること(1手前のマスはもう空白になっている)。
出題の前提:平成19年度春期基本情報技術者試験午後問12の出題条件に基づく
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.43 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.44 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.45 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.46 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.47 ↗(cdn.fe-siken.com)
アセンブラ(CASL II)によるメモリプール管理プログラムの作成と追跡
プログラミング · CASL II / メモリ管理 / ビット演算 / テーブルジャンプ
メモリプールの管理を行うCASL II副プログラムMPMGRについて、プログラム中の空欄[ a ]〜[ d ]及び設問2の問いに答えよ。 【プログラムの説明】 (1) メモリプールは要素領域と管理領域からなり、要素領域は80要素(各要素2語)から構成される。各要素には管理領域の1ビットが順に対応し、1のとき使用中、0のとき未使用を表す。 (2) GR1の値に応じて、0: 初期化(MINI)、1: 要素の割当て(MSER)、2: 要素の返却(MREL) を実行する。 〔設問1〕プログラム中の空欄[ a ]〜[ d ]に入れる正しい答えを選択肢から選べ。 〔設問2〕管理領域の最初の語の値が #C800 のとき、GR1に1を設定してMPMGRを呼び出した。ラベル FIND に制御が移ったときのGR3の内容を選べ。
- 設問1 a エ
- JUMP 0,GR1
- 設問1 b カ
- JOV LP2
- 設問1 c イ
- OR GR7,GR1
- 設問1 d カ
- XOR GR1,=#FFFF
- 設問2 ウ
- 2
解答・解説を表示
解答
設問1 a: エ, 設問1 b: カ, 設問1 c: イ, 設問1 d: カ, 設問2: ウ
解説
まず要点:アセンブラの論理左シフト命令(SLL)は、レジスタから押し出された最後のビットがOF(あふれフラグ)に入ります。ビットの管理では、あるビットを1にするにはOR、0にするにはそのビットだけ0のマスクとのANDを使い、マスクを作る反転には全ビット1(#FFFF)とのXORを使います。
解き方
- 分岐の処理:LTBLから取り出した飛び先の番地がGR1に入っているので、指標修飾を使って0番地+GR1の位置へJUMPします。
- 割当ての検索:SLL GR7,1で押し出されたビットの値(使用中なら1)がOFに入るので、JOV命令で次のビットへ進みます。0ならジャンプせず直後のFINDへ進みます。
- ビットの更新:割当てのときは対象ビットを1にするためOR、返却のときは反転したマスクで対象ビットを0にするため、XOR #FFFFのあとにANDを行います。
- 追跡の計算:#C800は2進数で「1100…」なので、0番目と1番目が1、2番目が0になり、GR3が2のときに空きが見つかります。
小問ごとの答え
- 小問 設問1 a:エ
- 直前のLD GR1,LTBL,GR1によってGR1には分岐先の先頭アドレスが格納されているため、JUMP 0,GR1によってGR1が指すアドレスへ無条件分岐します。
- 小問 設問1 b:カ
- SLL GR7,1で押し出されたビットが1(使用中)の場合、COMET IIの仕様によりOFが1になります。未使用ビット(0)を探すため、OF=1のときは次のビットを調べるべくJOV LP2でループ先頭へ分岐します。
- 小問 設問1 c:イ
- GR1には対象ビットのみが1となったマスクパターンが保持されています。該当要素を使用中(1)にするため、OR GR7,GR1によって対象ビットを1に設定します。
- 小問 設問1 d:カ
- 対象ビットを未使用(0)にするため、該当ビットのみ0で他が1のマスクを作る必要があります。全ビットが1である#FFFFとXOR演算を行うことでGR1の全ビットを反転させます。
- 小問 設問2:ウ
- #C800を2進数で表すと1100 1000 0000 0000です。最上位(GR3=0)は1、次(GR3=1)も1ですが、3番目(GR3=2)が0(未使用)となるため、ここでループを抜けてFINDに移行します。したがってGR3の値は2です。
覚えるポイント
- COMET IIのSLL/SRL命令では、最後に押し出されたビットがOFに設定される。
- 特定ビットのみを0にクリアするには、反転マスク(XOR =#FFFF)を作ってAND演算を行う。
間違えやすいところ
- JUMP LTBL,GR1と書くと、GR1番地ではなくLTBL+GR1番地の命令を実行しようとしてしまう点。
- JOVとJZE・JNZを混同し、シフトの結果そのものが0かの判定と、押し出されたビットの判定を間違えること。
出題の前提:基本情報技術者試験(アセンブラ言語 CASL II・COMET II 仕様)
出典:IPA(PDF保管先:基本情報技術者試験ドットコム)『2007年度 春期 午後』
IPA公式問題冊子(第三者保管の保存版) p.48 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.49 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.50 ↗(cdn.fe-siken.com) / IPA公式問題冊子(第三者保管の保存版) p.51 ↗(cdn.fe-siken.com)
2007年度 春期 午後
参照した公式資料
IPA(PDF保管先:基本情報技術者試験ドットコム)が公開した2007年度 春期 午後の問題・解答資料です。
- IPA公式問題冊子(第三者保管の保存版) ↗ — cdn.fe-siken.com(PDF・64ページ)
- IPA公式解答例(第三者保管の保存版) ↗ — cdn.fe-siken.com(PDF・4ページ)

