━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ データ構造・アルゴリズム論 確認問題12 ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━
●問 (マージソート) データ列 7, 5, 2, 1, 3 を配列に格納して,授業で扱った(教科書の) マージソートで値を小さい順に並べ替える. (1) 関数 msort(p, n) の呼び出し順を,各呼び出しでの実引き数の対 (p, n) の 列として((1,5), (2,3), (3,1), (4,1) などの形式で)表せ. ここで,p は配列の開始位置を,n は要素数を表す. (2) 配列の変化を(授業で扱ったのと同じ形式で)示せ. ────────────────────────────────────── ●答 (マージソート) (1) (1,5) (1,2) (1,1) (2,1) (3,3) (3,1) (4,2) (4,1) (5,1) (2) 実行前 [7, 5, 2, 1, 3] 途中結果 [7, 5][2, 1, 3] [7][5][2, 1, 3] [5, 7][2, 1, 3] [5, 7][2][1, 3] [5, 7][2][1][3] [5, 7][2][1, 3] [5, 7][1, 2, 3] [1, 2, 3, 5, 7] [解説] 再帰関数の呼び出し順を考えるには,呼び出しの木を使うとよい. これは,実引き数の組を節点とし,呼び出す引き数の組を子とする木である. この木を先行順(深さ優先順)に走査すると,呼び出し順の系列が得られる. 上記の解答 (1) の系列は,教科書のマージソートの関数 msort(p, n) の 呼び出しの木(下図)を先行順に走査して得られる. (1,5) / \ (1,2) (3,3) / \ / \ (1,1) (2,1) (3,1) (4,2) / \ (4,1) (5,1) 上記の解答 (2) では,関数 msort(p, n) の整列対象の要素数 n が 2以上の場合に(つまり,呼び出しの木の葉以外の節点で), 関数の実行直前と実行直後での配列の中身を示した. n≧2 の場合,整列の開始位置 p から n 要素の部分配列を前半部分と後半部分に分け, それぞれをマージソートで再帰的に整列して,結果をマージする. 教科書のアルゴリズムでは分割時の前半の長さは n を2で割った商なので, n が奇数なら後半より長さが1短くなる.左右の長さを入れ替えると動作は変わるが, どちらの分割方法でも呼び出し木は平衡木になるので,同じ計算量で整列できる. ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 授業のホームページ 山田 俊行 https://www.cs.info.mie-u.ac.jp/~toshi/