目次
はじめに
今回も、応用情報技術者試験の過去問を解いていきます。
一見すると「ただのメモリ転送の問題」に見えますが、実は かなり重要な概念(実務でも頻出) が含まれています。
特に、
- なぜ選択肢アがダメなのか?
- 「同一メモリ空間」の意味は何か?
このあたりを、直感的に理解できるように解説していきます。
問題
同一メモリ空間で,転送元の開始アドレス,転送先の開始アドレス,方向フラグ及び転送語数をパラメータとして指定することによって,データをブロック転送できる機能をもつCPUがある。
図のようにアドレス1001から1004のデータをアドレス1003から1006に転送するとき,指定するパラメータとして適切なものはどれか。ここで,転送は開始アドレスから1語ずつ行われ,方向フラグに0を指定するとアドレスの昇順に,1を指定するとアドレスの降順に転送を行うものとする。
同一メモリ空間で,転送元の開始アドレス,転送先の開始アドレス,方向フラグ及び転送語数を指定することで,データをブロック転送できるCPUがある。
アドレス1001~1004のデータを,1003~1006へ転送する。
方向フラグ:
- 0:アドレス昇順
- 1:アドレス降順
適切なパラメータはどれか。

| 選択肢 | 転送元 | 転送先 | 方向 | 語数 |
|---|---|---|---|---|
| ア | 1001 | 1003 | 0 | 4 |
| イ | 1001 | 1003 | 1 | 4 |
| ウ | 1004 | 1006 | 0 | 4 |
| エ | 1004 | 1006 | 1 | 4 |
解答
👉 エ
解説…の前に
この問題を最初見た時、こう思いました
「ア、はなんで正しくないのか?」
しばらく考えてから、その理由に気づきましたが、
もしかすると私と同じような疑問を持った人もいるのではないでしょうか。
そんな人に向けて、この問題を別の形に置き換えてみようと思います。
本質の部分は同じなので、この置き換え問題を解くことで
元々の問題に解答できたことになります
■ この問題の本質を別の例で考える
● 設定:引き出しとボールの話
8個の引き出しが並んだ棚があるとします。
引き出し番号:1000 1001 1002 1003 1004 1005 1006 1007
ここに、最初は次のようなアルファベット名のボールが入っています。
1001:A
1002:B
1003:C
1004:D
● ルール(これが超重要)
この棚には次のルールがあります(ちょっと特殊ですが…):
- 引き出しには 1つしかボールを入れられない
- 新しいボールを入れると、元のボールは消える(上書き)
- ボールは1個ずつ順番に移動する
👉 これが「同一メモリ」の意味です
(同じ場所に上書きされる世界)
人によっては、問題の図を見て、2つの場所での移動を行うと思った方もいるかもしれません。
ですがそうではなく、1つの場所での移動の問題なのです。
● やりたいこと
次のように移動したい:
1001 → 1003
1002 → 1004
1003 → 1005
1004 → 1006
つまり:
[A B C D] を右に2つずらしたい
■ パターン①:普通に前から入れてみる(=選択肢ア)
順番にやると:
① Aを1003へ
1003:A(もともと入っていたCは消える)
② Bを1004へ
1004:B(もともと入っていたDは消える)
③ Cを1005へ
👉 でもここで問題!
- 本来のCはもう消えている(Aに上書きされた)
結果
👉 データが壊れる
● なぜダメか
👉 「まだ使うボールを先に消してしまった」
これが選択肢アが間違いの理由です。
■ パターン②:後ろから入れる(=正解(エ)の方法)
今度は逆にやります👇
① Dを1006へ
(安全)
② Cを1005へ
(まだ残ってるのでOK)
③ Bを1004へ
④ Aを1003へ
● 結果
👉 すべて正しく移動できる
■ この問題の正体
この引き出しの話をそのまま言い換えると:
| 引き出し(置き換えた問題) | メモリ(元々の問題) |
|---|---|
| ボール | データ |
| 上書き | メモリ破壊 |
| 順番に入れる | 1語ずつ転送 |
| 同じ棚 | 同一メモリ |
■ まとめ(核心)
👉 この問題の本質はこれ
- 同じ場所にコピーする(同一メモリ)
- コピー元とコピー先が重なっている
- だから順番を間違えるとデータが壊れる
解説
では、改めて、問題の解説を行います。
これまでの説明とほぼ同じなので、不要な人は読み飛ばしてください。
■ この問題の違和感の正体
この問題のポイントはここです👇
👉 同一メモリ空間
つまり:
- コピー元とコピー先が同じ場所に存在する
- 上書きが発生する
■ NGパターン(選択肢ア)
昇順でコピーすると…
① A → 1003(Cが消える)
② B → 1004(Dが消える)
③ C → 1005 ← もうCは存在しない!
■ なぜダメか
👉 まだ使うデータを先に消してしまったから
■ 正しい方法(後ろからコピー)
降順で実行
① D → 1006
② C → 1005
③ B → 1004
④ A → 1003
■ ポイント
👉 元データを壊さない順番でコピーしている
■ 結論
| 項目 | 値 |
|---|---|
| 転送元 | 1004 |
| 転送先 | 1006 |
| 方向 | 1(降順) |
| 語数 | 4 |
👉 よって エ
イとウが違う理由
この問題の選択肢 イとウは不正解です。
念のため、それらが間違っている理由も説明します。
■ まずそれぞれの意味を確認
| 選択肢 | 転送元 | 転送先 | 方向 | 意味 |
|---|---|---|---|---|
| イ | 1001 | 1003 | 1 | 前のアドレスから“後ろ向き”にコピー |
| ウ | 1004 | 1006 | 0 | 後ろのアドレスから“前向き”にコピー |
■ イの問題点
▼ イの動き
方向フラグ=1(降順)なので
1001 → 1003
1000 → 1002
999 → 1001 ...
👉 つまり「1001から逆方向に進む」
■ 何が問題か
👉 コピーしたい範囲がズレている
本来やりたいのは:
1001~1004 → 1003~1006
しかしイでは:
- 1004がコピー対象に入らない
- 1000など不要な領域を読んでしまう
■ 結論
👉 コピー範囲の指定が間違っている
■ ウの問題点
▼ ウの動き
方向フラグ=0(昇順)
1004 → 1006
1005 → 1007
1006 → 1008 ...
■ 何が問題か
👉 そもそもコピー元がズレている
本来コピーしたいのは:
1001,1002,1003,1004
しかしウでは:
1004,1005,1006,1007
👉 全然違うデータをコピーしている
■ 結論
👉 コピー範囲の指定が間違っている
問題の用語解説
■ 同一メモリ空間
同じメモリ領域内でデータを移動すること
👉 特徴:
- コピー元とコピー先が重なることがある
- 上書きによるデータ破壊のリスクあり
■ 方向フラグ
コピーの順番を制御する
| 値 | 意味 |
|---|---|
| 0 | 昇順(前から) |
| 1 | 降順(後ろから) |
■ ブロック転送
複数のデータをまとめて転送する処理
体系的位置づけ
この問題は以下の分野に属します:
- コンピュータアーキテクチャ
- メモリ管理
- データ転送処理
この技術はどこで使われているのか
この問題で問われているのは👇
👉 「同一メモリ内での安全なデータ移動(重なり対応コピー)」
一見すると試験用の特殊な話に見えますが、実際には かなり幅広い分野で使われている基礎技術 です。
■ ① 配列・データ構造の操作(最も身近)
例えば配列から要素を削除する場合:
▼ 削除前
[ A B C D E ]
▼ Bを削除
[ A C D E ]
■ 内部で何が起きているか
C → Bの位置へ
D → Cの位置へ
E → Dの位置へ
👉 同一メモリ内コピーが発生
■ ② 文字列処理
文字列の一部を削除する場合:
"ABCDE" → "ACDE"
■ 内部処理
C → Bへ
D → Cへ
E → Dへ
👉 これも完全に同じ問題
■ ③ OS(オペレーティングシステム)
OSは常にメモリを整理しています。
■ 代表例:メモリの詰め処理(コンパクション)
[プロセスA][空き][プロセスB]
👉 空きをなくすために移動
[プロセスA][プロセスB][空き]
👉 このとき内部では
重なりを考慮したコピー処理 が行われています
■ ④ ネットワーク・ストリーム処理
受信バッファの例:
[処理済][未処理データ][空き]
■ 処理後
未処理データを先頭へ移動
👉 ここでも
同一メモリ内でのデータ移動
■ ⑤ ファイル・データ処理
ログやファイルバッファでも:
[古いデータ][新しいデータ]
👉 古いデータ削除 → 前に詰める
■ ⑥ プログラミング言語の内部実装
C言語などでは次の関数で実装されています:
memcpy() // 重なりNG(高速)
memmove() // 重なりOK(安全)
👉 今回の問題はまさに
👉 memmoveの内部ロジック
■ ⑦ CPU・ハードウェアレベル
CPUには以下のような命令があります:
- ブロック転送命令(REP MOVS など)
- DMA(直接メモリアクセス)
👉 これらも同様に
転送方向を制御して安全にコピー
■ 小まとめ
用途 → 共通していること
--------------------------------------
配列操作 → データを詰める
文字列処理 → 一部削除
OS → メモリ整理
ネットワーク → バッファ調整
C言語 → memmove
CPU命令 → ブロック転送
この問題から得られる教訓
👉 同一メモリ内でのコピーは順番を誤るとデータが消える
メモリが重なっている状態で前からコピーすると、
まだ使うデータを先に上書きしてしまい、正しい結果が得られなくなる。
■ 重要ポイント
- 同一メモリでは上書きが発生する
- 順番を誤るとデータ破壊につながる
- 重なりがある場合は「後ろからコピー」が基本
👉 「データ移動は順番が命」
まとめ
今回のポイントは非常にシンプルです👇
■ 覚えるべきこと
👉 メモリが重なるときは後ろからコピーする
■ なぜか?
- 前からコピー → データが消える
- 後ろからコピー → 安全
■ 本質
👉 順番を間違えると「情報が壊れる」
参考情報
- IPA 応用情報技術者試験 過去問題:
https://www.ipa.go.jp/shiken/mondai-kaiotu/2024r06.html

コメント