Upgrade to Pro — share decks privately, control downloads, hide ads and more …

SQLAP#1

kentana20
November 29, 2013

 SQLAP#1

Presentation document for inside workshop for ikyu corp(www.ikyu.co.jp).
The theme is 2nd part of SQL Antipattern "Naive Tree".

kentana20

November 29, 2013
Tweet

More Decks by kentana20

Other Decks in Programming

Transcript

  1. 本日のアジェンダ • はじめに ◦ SQLアンチパターン本について • 本編 ◦ 2章:ナイーブツリー(素朴な木) ◦

    3章:IDリクワイアド(とりあえずID) • ダイアログディスカッション • クロージング
  2. 本日のアジェンダ • はじめに ◦ SQLアンチパターン本について • 本編 ◦ 2章:ナイーブツリー(素朴な木) ◦

    3章:IDリクワイアド(とりあえずID) • ダイアログディスカッション • クロージング
  3. 本日のアジェンダ • はじめに ◦ SQLアンチパターン本について • 本編 ◦ 2章:ナイーブツリー(素朴な木) ◦

    3章:IDリクワイアド(とりあえずID) • ダイアログディスカッション • クロージング
  4. ナイーブツリー(素朴な木) 営業本部 bar営業部 foo営業部 fuga課 hoge課 piyo課 hogera係 ルート •

    ツリー構造のエントリ ◦ ルート(根) ◦ 非葉ノード ◦ リーフ(葉) 非葉ノード リーフ
  5. ナイーブツリー(素朴な木) • ツリー構造を用いる一般事例 ◦ 組織図 ◦ 掲示板のコメント(スレッド) • 一休での事例 ◦

    宿泊 :エリアマスタ(特大 > 大 > 小) ◦ Nexus:投稿・コメント(投稿 > コメント)
  6. ナイーブツリー(素朴な木) • 階層制限が無いとツラい件 ◦ あるノードを元にして2階層を取得するSQL -- foo営業部が所属している本部を求める SQL SELECT ORG2.section_id,

    ORG2.section_name FROM tbl_organization AS ORG1 -- 子 LEFT OUTER JOIN tbl_organization AS ORG2 -- 親 ON ORG1.parent_id = ORG2.section_id WHERE C1.section_id = ‘ 2’ -- 2:foo 営業部
  7. ナイーブツリー(素朴な木) • 階層制限が無いとツラい件 ◦ あるノードを元にして2階層を取得するSQL -- foo営業部が所属している本部を求める SQL SELECT ORG2.section_id,

    ORG2.section_name FROM tbl_organization AS ORG1 -- 子 LEFT OUTER JOIN tbl_organization AS ORG2 -- 親 ON ORG1.parent_id = ORG2.section_id WHERE C1.section_id = ‘ 2’ -- 2:foo 営業部
  8. ナイーブツリー(素朴な木) • 階層制限が無いとツラい件 ◦ あるノードを元にして3階層を取得するSQL -- hoge課が所属する部と本部を求める SQL SELECT ORG3.section_id,

    ORG3.section_name , ORG2.section_id, ORG2.section_name FROM tbl_organization AS ORG1 -- 子 LEFT OUTER JOIN tbl_organization AS ORG2 -- 親 ON ORG1.parent_id = ORG2.section_id LEFT OUTER JOIN tbl_organization AS ORG3 -- 親の親 ON ORG2.parent_id = ORG3.section_id WHERE C1.section_id = ‘ 2’ -- 2:foo 営業部
  9. ナイーブツリー(素朴な木) • 中間ノードの削除時の更新が大変な件 ◦ hoge課とhogera係が統合のため、hoge・ra課に! -- hoge・ra課誕生のためのSQL -- 1.hogera係レコードの更新 UPDATE

    tbl_organization SET parent_id = ‘2’ , section_name = ‘hoge ・ra課’ WHERE section_id = ‘5’; -- 2. hoge課レコードの削除 DELETE FROM tbl_organization WHERE section_id = ‘4’;
  10. ナイーブツリー(素朴な木) • 経路列挙型モデル ◦ デメリット ▪ 経路を文字列で保持しているため、パスの完全性を保証 できず、アプリケーションの実装に依存してしまう ▪ パス文字列(文字数)には上限が設定されるため階層数

    には制限が生まれる ▪ 中間ノード(非葉ノード)の削除の手間は変わらない ‘ 追加するノードまでのパスを生成 Dim path path = getCurrentNodePath() & ‘/’ & newNode ‘ 若干危うい・・・ ‘ 追加するパスをprepare statement へセット cmd.Parameters.Add(‘@path’, path)
  11. ナイーブツリー(素朴な木) • 入れ子集合型モデル ◦ メリット ▪ 中間ノード(非葉ノード)を削除した時の更新処理が不要 (該当ノードの削除のみでOK) ▪ 部分ノードの取得も簡単

    -- foo営業部配下の部、課を取得するための SQL SELECT ORG2.* FROM tbl_organization AS ORG1 INNER JOIN tbl_organization AS ORG2 ON ORG2.ns_left BETWEEN ORG1.ns_left AND ORG2.ns_right WHERE ORG1.section_id = ‘2’ -- 2:foo 営業部;
  12. ナイーブツリー(素朴な木) • 入れ子集合型モデル ◦ デメリット ▪ 直近の親を抽出するSQLが若干複雑になる -- hoge課が所属する部を取得するための SQL

    SELECT ORG_PARENT.* FROM tbl_organization AS ORG1 INNER JOIN tbl_organization AS ORG_PARENT ON ORG_PARENT.ns_left < ORG1.ns_left -- hoge 課のns_leftより小さい AND ORG1.ns_left < ORG_PARENT.ns_right -- hoge 課のns_leftより大きい LEFT OUTER JOIN tbl_organization AS ORG_BETWEEN ON ORG_BETWEEN.ns_left < ORG1.ns_left -- hoge 課のns_leftより小さい AND ORG1.ns_left < ORG_BETWEEN.ns_right -- hoge 課のns_leftより大きい AND ORG_PARENT.ns_left < ORG_BETWEEN.ns_left -- 中間のns_leftより大きい AND ORG_BETWEEN.ns_left < ORG_PARENT.ns_right -- 中間のns_leftより大きい WHERE ORG1.section_id = ‘4’ -- 4:hoge 課 AND ORG_BETWEEN.section_id IS NULL;
  13. ナイーブツリー(素朴な木) • 閉包テーブル型モデル ◦ メリット ▪ 閉包テーブルを用いれば部分ノードや親へのパスの取 得が簡単(入れ子集合型より簡単) ▪ データの関連が直感的

    ▪ ノードの追加や削除もラク -- foo営業部配下の部、課を取得するための SQL SELECT ORG.* FROM tbl_organization AS ORG INNER JOIN tbl_closure AS CLS ON ORG.section_id = CLS.child_id WHERE CLS.parent_id = ‘2’ -- 2:foo 営業部;
  14. 本日のアジェンダ • はじめに ◦ SQLアンチパターン本について • 本編 ◦ 2章:ナイーブツリー(素朴な木) ◦

    3章:IDリクワイアド(とりあえずID) • ダイアログディスカッション • クロージング
  15. 本日のアジェンダ • はじめに ◦ SQLアンチパターン本について • 本編 ◦ 2章:ナイーブツリー(素朴な木) ◦

    3章:IDリクワイアド(とりあえずID) • ダイアログディスカッション • クロージング
  16. ナイーブツリー(素朴な木) • まとめ ◦ アンチパターン ▪ 隣接ツリー型 • わかりやすいが、ナイーブ ◦

    解決法 ▪ 経路列挙型 • 視認しやすいが、文字列ゆえの脆弱さ ▪ 入れ子集合型 • わかりづらっ ▪ 閉包テーブル型 • 管理しやすいが、データ量に難あり
  17. ナイーブツリー(素朴な木) • まとめ ◦ ツリー構造を採用する物理モデルはどのサービスにも頻出 する、「あるある」パターン ◦ どの方法もメリット、デメリットがある ◦ 設計時に”こういう解決策もあるんだよね”という心の引き出し

    として装備しておくことが大事(適材適所の選択が大切) ◦ 要件がブレない、ブレさせない(未来も含めて)場合はアンチ パターンを選択する事も正解となる