データ構造とアルゴリズム
第二回
(2010年10月1日)
アルゴリズムの表現と評価
http://www.sw.it.aoyama.ac.jp/2010/DA/lecture2.html
Martin J. Dürst
© 2008-10 Martin
J. Dürst 青山学院大学
目次
- 前回のまとめ・宿題
- アルゴリズムの表現方法
- プログラム言語 Ruby
- アルゴリズムの評価
前回のまとめ
- 授業の位置づけと進め方
- アルゴリズムとデータ構造の魅力
- データ構造の概要 (例: 連結リスト)
- アルゴリズムの概要 (例: 線形探索、2分探索)
宿題 1: 膨大なデータ
提出: 来週の木曜日 (9月30日) 19時00分締切、O 棟
529号室の前に提出
- 東京証券取引所の第一部の取引で、一株式会社の株が営業時間内に平均で4分に一回売買されていると想定して、合計で年間に何項目ぐらいのデータが集まるのかを、想定の根拠も書きながら計算しなさい。
- Google (又は明記の上で他のサーチエンジン)
が対応しているウェブページの数と平均のページあたりのリンク数を調べ、おおよその合計のリンク数を計算しなさい。
- 問題 1 や 2
の結果よりも大きくて実際に存在しうるデータ項目の量を考え、説明しなさい
(他人と同じものの場合には減点の対象となる)。
アルゴリズムの表現方法
問題: アルゴリズムをどうやって表現するか
文書
利点:
欠点:
- 文書の曖昧さ
- 正確な表現の限界
- 構造が不明
- 自然言語に依存
図
例: 流れ図など
利点:
欠点:
- 作成の手間
- データ交換の困難
- 構造化プログラミングとの隔たり
(構造化プログラミング (structured programming): goto
(プログラム内の任意のところへのジャンプ)
の代わり、入れ子になっている枝分れ、繰返しなどの使用)
疑似コード
(pseudocode)
利点:
- 自然言語とプログラムの中間
- アルゴリズムの本質に注目が可能
- 構造化プログラミングと連結
欠点:
プログラム言語
利点:
欠点:
- 種類が多い
- アルゴリズムの本質と違う
- 必要以上に細かい
Ruby プログラム言語
- 日本発 (まつもと ゆきひろが 1993 年から開発)
- 2000年から欧米でも人気を集める
- 2004年から Ruby on Rails
で更に注目
- 完全なオブジェクト指向
- 手軽なスクリプト言語
- 初心者にやさしいが、上級者も大満足
- 卒論などで使用、実装に貢献 (国際化)
Ruby のインストールの確認
アルゴリズム表現のための Ruby
- 簡潔な記法
- 変数の宣言が不要
- 型の互換性はメソッドで決まる (いわゆる duck
typing)
- 「動く疑似コード」
- プロファイラなど環境の充実
最初の Ruby の例
線形探索と二分探索: 2search.rb
実行: コマンドプロンプトで ruby 2search.rb
Ruby の記法の基本
- 行末に
;
(セミコロン) が不要
- メソッド (関数) 呼び出しで一部
()
が不要
- メソッド (関数) の定義は
def
で
class
/def
/if
/while
/do
などに必ず end
が必要
アルゴリズムの評価の概要
評価のときに必要な情報:
実行時間の比較: 具体から抽象へ
- 実行時間の測定
- ステップの数え上げ
- 最悪の場合のステップの数え上げ
- 漸近記号
実行時間の比較: 計測
- 利点:
(条件が合えば) 正確な結果
- 問題点
- ハードウェアによって結果が違う
- 実装の詳細によって結果が違う
- 実行するたびに結果が少し違う
- 実装が前提
⇒ もっと抽象的な比較方法が必要
実行時間の比較: ステップの数え上げ
(ステップ:
一定時間で計算可能な部分、例えば演算、比較など)
- 利点
ハードウェア依存無し
- 問題点
- 実装によってステップの数が違う
- ステップの数え方は様々
- 入力項目の数や種類によってステップ数が違う
⇒ もっと抽象的な比較方法が必要
漸近的な増加の例
(asymptotic growth)
ステップの数
n (データの個数) |
1 |
10 |
100 |
1,000 |
10,000 |
100,000 |
1,000,000 |
線形探索 |
|
|
|
|
|
|
|
2分探索 |
|
|
|
|
|
|
|
ステップの数を式で表すとどうなる
データの個数が多くなると式のどの項が重くなる
漸近的な増加の考え方
- アルゴリズムの計算時間やステップ数は入力項目の数にどのように依存
- 依存を関数で表す: f(入力項目数)
- 関数の比較に使う原則:
- 入力項目数が少ないときの差を無視
- 一定時間の差は無視 (例えば初期化用)
- 定数倍の差を無視 (ハードの進化で対応可能)
⇒ アルゴリズムの本質的な差が表せる
漸近記号: O の定義
("big Oh" notation)
- ある関数 f(n)
- の漸近的上界 (asymtotic upper bound) を表す
- もう一つの関数 g (n) があるときに
- f (n) = O(g (n))
と書く
- この条件として、
- 全ての n > n0 において、0
≤ f (n) ≤ cg
(n) となる
- 正の定数 n0 と c
が存在する
まとめ
- アルゴリズムの表現方法は様々
- この授業では「動く疑似コード」の Ruby を使用
- アルゴリズムの評価の中心は実行時間の漸近的な増加
(計算量)
- 漸近的な増加の上界は O 記法で表す