方法 - みる会図書館


検索対象: 月刊 C MAGAZINE 2001年9月号
76件見つかりました。

1. 月刊 C MAGAZINE 2001年9月号

最新システム 開発技法 XML データベース十 Web アプリケー ション 原忠司 , 加藤賢之 , 坂口良 ( 株 ) メディアフュージョン XMLLab 現在のシステム開発では , XML を用いたデータベ し , XML の実践的な利用方法について紹介しま ースシステムと , そのクライアントとしての Web す。 XML ドキュメントをデータベースに格納して アプリケーションの開発が主流になりつつありま 検索する方法を解説し , Web アプリケーションの す。実際にそのような開発に携わっている方も多 開発スタイル , それらを統合したプログラムの開 いと思います。また , 私たちがユーザとしてその 発方法を示します。また , これらのシステムでは ようなシステムを知らずに利用していることもよ 必要性が増えてきている「並列処理」のプログラミ くあります。本特集では , こうしたシステム開発 ング方法に 0 いて紹介します。本特集が : システ で実際に行われているさまざまな開発手法を解説 ム構築の理解への一助となれば幸いです XML ドキュメントの格納と検索 原忠司 ( ( 株 ) メディアフュージョン XML Lab) XML をデータベースに格納して利用していくうえでもっとも問題になるのは 「データベースへの格納方法」と「検索方法」です。 XML が持つ構造を生かしたま までこれらを行うには , いくつかの方法があります。本章ではリレーショナル データベースでの問題点と XML 専用データストアを用いた方法を解説します。 が , 逆に今こそ XML とは何かが理解され , 解が深まり , 現在ではサーバアプリケーシ はじめに 実際の業務にどう役立てるかを考える時期 ョン , または組み込み用アプリケーション が訪れたといえます。 の開発言語として , 確固たる地位を築いて 最近の IT 関連の話題で , XML[ 注 1] は必ず これと同じような傾向は , Java でも見ら います。 あげられるものの 1 っといえるでしよう。 れました。 Java も当初は本質があまり理解 XML も Java と同じような道をたどるとす 時期の出版ラッシュに見るような盛り上が されず , プームに押し上げられた感があり れば , 今から XML についてあらためて考え , りからするとやや落ち着いた感があります ましたが , それが一段落した後 , 徐々に理 その有効性を考える必要があるのではない 22 C MAGAZINE 2001 9

2. 月刊 C MAGAZINE 2001年9月号

ネットワークプロクラミンクのアトリエ ントも増えてきましたが , その対応の度合 の利用には向かない方法です。 持っことを想定します。 いはまちまちのようです。 IMAP は , 大き ・切断モデル ・メールポックスの一覧の取得 く分けて 3 つの使い方ができるように設計 奇妙な名前ですが , 意味的には「間欠接 ・メッセージー覧の取得 されており , どの使い方であるかによって 続モデル」とでも呼べる方法です。必要な ・ヘッダの取得 対応の度合いが大きく違ってくるプロトコ ときにだけ IMAP サーバに接続し , メッセ ・ MIME ヘッダの取得 ルです。 ージなどを取得したら接続を切ってオフラ ・本文の取得 IMAP クライアントの実装方法には , イン状態でメッセージを扱います。必要な ・ MIME パートの取得 ・オフラインモデル ときにのみ接続するので , モバイルやダイ これ以外にもメールポックスの管理機能 ・オンラインモテル アルアップでの利用に向いている方法で などがありますが , GUI などと絡む部分が ・切断モテル す。 多いので本稿では解説しません。 があり , それぞれの実装に特徴があります。 余分な LOGIN, LOGOUT 処理やメッセ ・ AP の状態遷移 機能の違いを Table7 に示します。 ージのキャッシュ処理などが必要となるた まず , 実装に先立って , IMAP の状態遷 ・オフラインモデル め , 3 つのモデルのうちではいちばん実装 移について理解しておく必要があるでしょ オフラインモデルはもっとも簡単な IMA コストがかかる方法です。 う。 Fig. 1 が IMAP の状態遷移です。通常は P 対応の方法です。基本的には IMAP の INB ・推奨する実装モデル 4 つの状態があり , それぞれ使えるコマン OX だけを使います。メッセージの取り扱 いちばん柔軟な利用方法のある「切断モ ドには制限があります。各状態について解 い方は POP と同じです。 デル」を推奨しますが , 利用方法を限定す 説すると次のようになります。 IMAP を疑似的に POP として扱うだけな るならば「オンラインモデル」でもよいでし ・非認証済み ので , 新しくクライアントを実装するので よう。ただし , オンラインモデルそのまま ログインしていない状態です。通常 IMA あれば避けるべき方法でしよう。 ではサーバ負荷 , ネットワーク負荷の点で P サーバがグリーティングメッセージをク クライアントの実装方法は POP と同様で パフォーマンスが悪くなる可能性があるの ライアントに送信した後 , この状態になり す。 POP 対応のクライアントで補助的に 1 で , キャッシュ機構を採り入れるなどして , ます。 MAP に対応するなどの状況で使われるこ 負荷をクライアント側に分散したほうがよ とが多いようです。 いでしよう。 ・オンラインモデル オンラインモデルは , 常時クライアント が IMAP サーバに接続し , クライアント側 には最小限のメッセージ情報のコピーしか 持たない方法です。 クライアント実装コストは切断モデルに 比べると少なくなっています。 いちばん素直な実装方法とも言えますが , LAN 接続のような比較的広いネットワー ク帯域と常時接続環境が必要になります。 モバイルでの利用やダイアルアップ環境で TabIe 6 フリーで入手可能なⅣ AP サーバ コマンド名 ワシントン大学 (uw-imapd) CMU の Project Cy 「 us ()y 「 us imapd) TabIe 7 クライアント実装モデルの比較 特徴 複数クライアントの使用 最小限のサーバ接続時間 最小限のサーバ資源 最小限のクライアントディスク 複数のリモートメールボックス 高速立ち上げ 非オンラインでのメールの処理 Fig. 1 Ⅳ AP の状態遷移 初期接続とサーバの挨拶 AP プロトコルの使用例 ( 2 ) ( 3 ) 「推奨する実装モデル」に従って ( 要する に SGmaiI の実装 ^ ^ ; なわけですが ) IMAP の コマンドの使い方について解説します。誌 面の都合上 , すべてを解説するわけにはい きませんが , できる限り実装のポイントと なる部分を解説します。 ・クライアントの仕様 クライアントの機能として , 次の機能を 説明 http://www.washington.edu/imap/ http://asg.web.cmu.edu/cyrus/imapd/ 非認証済み ( 7 ) ( 4 ) 認証済み ( 7 ) ( 6 ) ( 5 ) 選択済み ( 7 ) ログアウトして接続を閉じる ( 1 ) 前もって認証なしの接続 ()K g 「 eeting) ( 2 ) 前もって認証された接続 (PREAUTH gre eting) ( 3 ) 拒否された接続 (BYE greeting) ( 4 ) 成功時の LOGIN または AUTHENT ℃ ATE ロ卩。和 (5) 成功時の SELECT または EXAMINE 命令 (6)CLOSE 命令 , または失敗した SELECT か EXAMINE 命令 (7)LOGOUT 命令 , サーバの閉鎖 . または接 続が閉じられた オフライン 〇 〇 〇 オンライン 〇 〇 〇 切断 〇〇 x x 〇 x 〇 109 技術を知って実践しよう ! ネットワークプログラミングのアトリエ

3. 月刊 C MAGAZINE 2001年9月号

W 血面 P 国「 m 加 tatsuya (tatsuya@exnet.com/ 第 21 回 第 データの共有 メッセージフック ( Part4 ) データの共有 これまで 3 回にわたり , メッセージをフックする術をいろいろ見てきました。マウスフック , キーボードフックなど使用頻度の高そうなフックや , システムに迫る Windows の各種メッセ ージフックなどです。今回はフックそのものではなく , フックまたは DLL を用いる場合に必要 な , データの共有について見ていきます。 今回のテーマのデータの共有ですが , み なさんはどのように実装していますか ? しかるべきデータをいったんディスク上に 書き込み , それを読み込む方法も考えられ ますし , 共通のメッセージを定義してデー タをやりとりする方法もあるでしよう。 単一プロセスならグローバルな変数でま かなえますが , Win32 のようなマルチスレ ッド OS で独立したプロセス間でのデータ 共有となると , 少しめんどうです。 Windo ws 3.1 などの W ⅲ 16 では , DLL などを用い ることでデータの共有は簡単に実現できま す。しかし Windows 95 以降や Windows NT などの Win32 では , 1 つ 1 つのプロセスごと に独立したメモリ空間を使用するので , のような方法は使えません。もっとも , プ ロセスごとに独立したメモリ空間を持っこ とで , 以前に比べればはるかに堅牢なアプ リケーションが作成できるのも事実です。 データ共有の方法 データを共有する方法はいくつかありま す。ここでは , 独立したプロセス空間での データの共有に絞っていきます。通常考え られる , または多く実装されている方法に は次の 3 つがあります。 ・パイプ ・メモリマッブドファイル ・メールスロット パイプは UN Ⅸなどでおなじみの入出力 1 22 C MAGAZINE 2 側 1 9 をそれぞれ結んでいく方法です。このほか にもいろいろありますが , 今回はメモリマ ッブドファイルを扱ってみます。 メモリマッブドファイルをひと言で言う と , 独立したプロセス空間で共有できるメ モリ空間を作成し , べつべつの実行ファイ ルが ( 独立したプロセス空間の ) お互い同 じ変数にアクセスするということです。ち ようどディスクに書き込んだデータをほか のアプリケーションで利用するのと似てい ます。ディスクがメモリに置き換わったと 思えばいいでしよう。 メモリマッブドファイルの利用イメージ メモリマッブドファイルを利用する場合 のフローは次のようになります。 ①メモリマッブドファイルをルールに従 って作成 ②メモリマッブドファイルを自分の独立 したメモリ空間にマッピングする ③そのマッピングしたメモリにデータの 書き込み , 読み込みを行う ④利用し終わったらメモリマッブドファ イルを解放する ⑤ハンドルのクローズ 物理的にディスクなどに書き込むのと同 じ流れだとわかるはずです。 メモリマッブドファイルの注意点 メモリマッブドファイルを利用する場合 に , 大きな問題が 1 つあります。それはや はりディスクに書き込む場合と同じで , デ ータの書き込みや読み込み時のデータへの 同時アクセスという問題です。たとえば A というアプリケーションでデータにアクセ ス中に B というアプリケーションがその データにアクセスして内容を変更すること がありえます。同時に同じ変数にアクセス した場合はそのデータの内容は保証されな くなるので , 同時アクセスの可能性がある 場合は , 何らかの方法でプロセス間の同期 をとる必要があります。 同期をとる方法として , 今回のサンプル プログラムではミューテックスオプジェク トを使用しています。ミューテックスオプ ジェクトとは , ほかのいかなるスレッドに も所有されていないときにシグナル状態 , ほかのプロセスに所有されているときに非 シグナル状態になります。一度に 1 つのス レッドだけがミューテックスを所有できる ので , データは保証されることになります。 / DLL 内での変数保持とフック 今までのメッセージフックのサンプルプ ログラムでは , DLL 内でメッセージフック のハンドルを共有変数として保存していま した。 DLL 内で宣言された変数は , まず DL L を呼び出したプロセスのアドレス空間に コピーされます。 DLL 内の変数はプロセス ごとにコピーされているので問題なく利用 できますが , システム全域にフックをかけ た場合はどうなるのでしようか ? キーポードフックなどのサンプルをもう 一度思い出してほしいのですが , 自分がア クテイプでなくても , キーポードから入力

4. 月刊 C MAGAZINE 2001年9月号

でしようか ? さて , XML を実際のシステム開発に利用 しようと考えたときにまず必要になるのが XML で表現したデータを格納する「データ ストア」だと思います。本章ではこの XML を格納するデータストアについて考えてみ ます。 ORACLE や SQL Server のような RDB とは違う , 最初から XML のために考えられ たデータベースの実装の 1 つである Yggdrasil 1 ( イグドラシル , Table 1 ) を通して , XML を格納するデータストアを考えてみたいと 田います。 [ 注 1]XML(eXtensibIe Markup Language) は 基本的には SGML から派生したマークアップ 言語です。 HTML とのいちばんの違いは , 自 由にタグを定義できるところです。 HTML や XML は W3C (http://www.w3.0「g/) が標準化を 行っています。 リレーショナルデータベースを 利用する まず最初に , 今までのシステム開発と同 様にリレーショナルデータベース ( 以下 RDB ) を利用して XML ドキュメントを格納する場 合を考えてみましよう。 もっとも単純な方法 データストアにリレーショナルデータベ ースを利用する場合 , 最初にわいてくる疑 Fig. 1 表の列として展開する方法 く ?xml version= 1 0 " ? > く住所録 > TabIe 1 名 発 特 称 徴 000 最新システム開発技法 Yggd 「 asill の概要 日本での開発により , 2 バイト文字の処理に対応 独自の検索アルゴリズム " St 「 uctu 「 e 引 ndex Algo 「 ithm " により高速検索を実現 DTD を必要としないウェルフォームド XML に対応 2001 年 6 月 29 日 2 ユーザライセンス 20 万円 ~ 無制限ユーザライセンス 100 万円 Yggd 「 asilll .0 ( fo 「 Windows) サーバ側動作環境 OS CPU OS HDD メモリ CPU メモリ HDD クライアント側動作環境 Windows NT Serve 「 4 ℃ ( SP4 以上 ) / 2000 Serve 「 100M バイト以上の空き容量 128M バイト以上 Pentium Ⅱ 233MHz 以上 Windows 98 / Me / 2000 ProfessionaI/NT 1 G バイト以上の空き容量 . 256M バイト以上 ( 推奨 512M バイト ) Pentiumm600MHz 以上 ( 株 ) メディアフュージョン TEL : 06-6415-2560 FAX . 06-6415-2556 問い合わせ先 Mail : info@mediafusion.co.jp URL : http://www.mediafusion.co.jp/ 問は , XML のツリー構造をどのようにして B の表形式に落とすのかだと思います。 もっとも単純でいちばん最初に思い浮か ぶ格納方法は , RDB の可変長文字列フィー ルドを用意し , そこに XML ドキュメントを 格納するという方法です。また場合によっ ては , XML ドキュメントから , 検索に利用 するノードを最初に決めておき , これを個 く個人名前 = " 僕小路俺麻呂 " > く住所 > 大阪市新宿区く / 住所 > く TEL > 999-8888V 几 EL > くコメント > 旧華族でおじゃるく / コメント > く / 住所録 > く / 個人 > 住所録テープレ 名前 僕小路俺麻呂 住所 大阪市新宿区 999-8888 TEL 特集 2 コメント 旧華族でおじゃる 別のフィールドに格納する場合もあるでし よう。 この方法だと , たしかに XML ドキュメン トを格納でき , その取得 / 更新にも使い慣 れた SQL を利用できます。しかし , 最初に 決めたキーとなるノード以外のノードで格 納した XML ドキュメントの中身を検索しよ うとした場合 , いったん格納された XML ド キュメントを読み出し , プログラムで XML ドキュメント内を検索するというような作 業が発生し , データストアの機能として XM L ドキュメントの検索を提供できなくなっ てしまいます。これでは XML ドキュメント を格納するデータストアとしてはあまり意 味がないでしよう。 表の列として展開する方法 そこで考えられた方法が , XML ドキュメ ントの各要素を表の列として展開して格納 する方法です。各要素をテープルの列とし て展開します。このとき , 要素の階層構造 は各テープルのリレーションとして表現し ます (Fig. 1 ) 。 比較的単純な変換で XML ドキュメントを 格納できました。このように格納すれば , 最新システム開発技法 XML テータベース + web アプリケーション

5. 月刊 C MAGAZINE 2001年9月号

す。一見するとメソッド呼び出しのように プロックを実行することができます。 Proc もともと , Ruby のイテレータは CLU とい 見えますが , yield は実際には予約語で , メ う言語のイテレータを参考にしているので オプジェクトを使うと , プロックの実行を 遅延することができるので , たとえば , GUI ソッドではありません。 yield は引数で渡さ すが , 取と CI の大きな違いは , CI の場 れた値をプロックに渡して実行し , プロッ アプリケーションでイベントハンドラを定 合はイテレータとメソッドはまったく別の ものであり , イテレータは値を返すことが 義するために利用することができます。 クが返した値を返します。 もう 1 つの方法はプロックを引数で Proc できないのに対し , Ruby の場合はイテレー ータを定義する オプジェクトとして受け取る方法です ( List タもメソッドであり , 値を返すことができ 19 ) 。メソッド定義の仮引数リストの最後 るということです。つまり , Ruby のイテレ それでは最後にイテレータを定義する方 に & 変数名 (List 19 では & block ) と記述する ータはもともとは繰り返しに利用するため 法を説明します。 ことで , プロックを Proc オプジェクトとし に考案されたのですが , 仕組み的には繰り 返しに特化したものではなく , メソッドに イテレータもメソッドなので , def によっ て受け取ることができます。プロックを実 行するためには Proc # ca Ⅱを呼び出せばよい コードを渡してコールバック的な処理を行 て定義します。問題はプロックを実行する 方法ですが , 2 通りの方法があります。 わけです。ただ , この方法の場合は , Proc うための , より一般的な仕組みなのです。 1 つは yield を使う方法です。 List 18 は IO オプジェクトを生成するコストがかかるた これは , たとえば C 言語なら関数ポインタ から 1 行ずつ読み込んで , プロックに読み め , yield よりも遅くなります。 を使って実現するような処理です。 Proc オプジェクトは , イテレータの呼び 込んだ行を渡して実行し , プロックが返し 繰り返さないイテレータの例 出し時に , foo( … , & block ) のように引数 た値を出力するイテレータの定義です ( pe の最後に & を付けて渡すことで , プロック それでは繰り返さないイテレータの例を という名前は nrby - pe からとりました ) 。プロ として渡すことができます。このため , 他の ックを実行するために yield を利用していま 見てみましよう。 イテレータにプロックをパスしたい場合に List 15 は配列の各要素を長さが小さい順 y 回 d の利用 は , プロックを Proc オプジェクトとして受 にソートする例です。各要素の比較を行う def ( i0 ) け取っておくと便利です。たとえば , List20 方法をプロックで指定しています。 C 言語 while line = iO. gets line yield(line) は再帰的なイテレータの例です。 Proc オプジ の qso れ ( ) を連想される方も多いのではない print ー ine ェクトとして受け取ったプロックを , 自分自 でしようか。 身を呼び出すときにそのまま渡しています。 List 16 は S ⅲ n sub の例です。 String#sub このように再帰的なイテレータも簡単に作 は文字列の置換を行うメソッドで , 第 1 引 数に正規表現 , 第 2 引数に置換文字列をと ることができます。 りますが , 第 2 引数を省略して代わりにプ 取後に ロックを与えることができます。プロック が与えられた場合 , 正規表現にマッチした 部分がプロックに渡され , その部分はプロ ックを実行した値で置換されます。 List 16 ではマッチした文字列を大文字にして置換 しています。 List 17 は Proc オプジェクトの利用例です。 通常のイテレータは , プロックを実行しま すが , Proc. new はプロックを実行する代わ りにⅣオプジェクト化して返します。 Pr oc オプジェクトは call というメソッドを持 っており , call メソッドを呼び出すことで pe(ARGF) do い土 n 司 line. upcase end &b lock の利用 def pe(io, &block) while line ま土 0. ge ヒ s line = block. call(line) print line イテレータを本連載 1 回ぶんの誌面で説 明するのはやはり無理があったかもしれま せん。舌足らずな説明でわかりにくい部分 も多いと思います。何か疑問があったら , 各 種書籍を参照したり , ruby-list ML や巧.com p. lang. ruby などで質問してください。 [ 参考文献 ] 田 mod-nlby , http://www.nrby-lang・ org/ en/raa-list. rhtml?name=mod ruby ・再帰的なイテレータ def foreachfile(file, &block) return if だ ( 基 . に . ) $ / = ~ File. khsenarne(file) block. call(file) if FiIe. directory?(file) Dir. foreach(file) d0 ぼ一 foreachfiIe(File. join(file, f), &block) foreachfile("/usr/lib/ruby") d0 国 p f end 88 C MAGAZINE 2 1 9

6. 月刊 C MAGAZINE 2001年9月号

000 最新システム開発技法 TabIe 2 List 2 を使用するときの記述方法 す。 Peer Web Se1Tice Server は , IIS のサプ 内容 設定 セット版にあたり , セキュリティ機能の一 旧 A 曰モジュールが存在する Web 部や管理ログ機能がないこと , ライセンス Scripts ( Ⅱ S をデフォルトインストールした場合のバス ) サーバ上の仮想バス によって接続数が 10 接続までに制限されて A 曰モジュール名 Pr0jectI . dll ( 作成した旧 A 曰 DLL 名 ) いるということを除けば , ほとんど違いは 関数名 Add ありません。小規模なイントラネットサー 関数への引数 Value=5 バとして利用するのであれば , PeerWebS e1ViceServer でも十分ともいえます。 ロセス ) でこれを実行できるようにしまし land Delphi 5 ( 以下 Delphi) の場合 , Web ア た。 ISAPI を利用すれば , IIS が提供する API プリケーション作成ウイザードがあるので , AP について を利用して , WWW サーバの機能を細かく 比較的簡単かと思います。本章では DeIphi 制御できると同時に , 実行時の負荷も軽減 での作成を中心に紹介します。 たとえば , W 、Ⅵクライアントからの入力 できるというメリットがあります。 実際に作成した DLL を IIS 上で動かすに に応じた処理を行うような場合 , 一般的な ISAPI を利用した拡張プログラムとして は , 作成した DLL を Web サーバ上の「 ISAPI 、ⅥⅥサーバでは , CGI(Common Gateway アプリケーション起動可能仮想パス」へコ は , WWW クライアントからの入力に応じ lnterface) と呼ばれるインタフェイスを使用 て何らかの処理を行う通常の拡張プログラ ピーしなければなりません (Fig. 7 ) 。また して , 外部プログラムを起動する方法が利 ム (ISAPI Extension) に加え , W Ⅵハサーバ IIS 設定ツールから , 登録した ISAPI アプリ 用されます ( Fig. ( a ) ) 。しかしこの方法で ケーションへのアクセスコントロールを設 とクライアント間でやりとりされる は外部プログラムは W Ⅵサーバとは異な データを監視して , 独自の認証プログラム 定しなければ実行することができません。 るプロセスとして実行されるため , 一般に やデータ圧縮などを行えるようにする ISAPI デバッグ方法 負荷の大きいプロセス生成処理をともない FiIter も作成できます。 ます。とくに複数の WWW クライアントか DeIphi で ISAPI アプリケーションをデバッ 実際に使ってみる らのアクセスが同時に実行される場合には , グするには , 一般的な実行モジュールとは この負荷が大きな問題になります。 違う方法をとらなければいけません。 1 つ 簡単な ISAPI アプリケーションを手始め の方法は , その ISAPI D 乢が存在するプロ これに対しⅡ S では , ISAPI と呼ばれるプ ログラムインタフェイスを用意しています に作ってみましよう。 ジェクト内に , もう 1 つ ISAPI インタフェイ (Fig. 6-(b))0 こうした WWWサーバの拡張 スを呼ぶ実行モジュールを作成することで 開発環境 機能を実現するプログラムを Windows NT す。 IIS が ISAPI インタフェイスを呼ぶよう の DLL (Dynamic Link Library) として作成 いろいろな開発環境で ISAPI アプリケー に任意の実行モジュールで ISAPI インタ できるようにし , IIS と同じコンテキスト ( プ ションの開発をサポートしていますが , Bor フェイスを呼ぶようにします。 Fig. 7 Ⅱ S の設定画面 Fig. 8 List 2 の実行画面 万イ非表示お知こ人り響ツトヘルプ ドレス 0 0 ノ / い“し & / P ′。第 , 1 、引レ ' ・ : 10 P 「 0 c 乢訓 20 インターネットインフォメーションサーど . Y 市川 0 . 訓 既定の FTP サイト止 ) 画を 0 y 訓 を 厭定の %b サイト 僞 m 田 Sa 田一 Printers 一コⅣ愴 す一コ - ⅶ - cnf ロ - ⅶ - 田口 - ⅶ 第ロ - ⅵ i - 釜ョコ -vti-txt 、まインターネットインフォメーションサービス ををリ 29 特集 2 最新システム開発技法 XML データベース + Web アプリケー ンヨン

7. 月刊 C MAGAZINE 2001年9月号

第 12 回 当たり判定 ( 後編 ) 久保裕一郎 / 宇治社中 (http://www.cc.「 im. 0 「 . jpFdeviIman/) 前回に引き続き , 3D 物体の当たり判定について , バウンディング ボリュームとその具体的な判定のしかたを解説します。 り判定はしなくてもよい」という刈り込み これらのようなムダを省くために , 今回 の効果です。この刈り込みは非常に効果的 はバウンディングボリュームについて説明 です。アプリケーションにもよりますが , を行います。 当たりそうな状況というのは , 当たりそう バウンディングボリューム 前回は当たり判定の前編として , 線分と もない状況よりはるかに少ないのです。さ 球など , 基本的な要素同士の当たり判定を バウンディングボリュームで引っか らに 説明しました。これらを組み合わせると , かったときに , あらためて内側の物体で当 ある物体の当たり判定を行うときに , 構 たり判定をするといった再帰的な方法をと 3D 空間におけるほとんどすべての形状を 成するボリゴンで判定するのではなく , 別 持つ物体同士で当たり判定が行えます。 ることにより , 総当たりとまったく同じ結 の単純な形状で判定を行う方法があります。 果を期待できます。ですから , バウンディ とはいっても , その効率は非常に悪いこ 先ほどの例でいえば , あなたがいる建物そ ングボリュームは近似ではないといえます。 とが予想できます。たとえばあなたが屋内 のものを籀で表現したり , 太陽や地球を球 次の利点は , このバウンディングボリュ で雑誌を読んでいるとします。一方 , 高速 ームの当たり判定のチェックが低コストで で表現するのです。このときの形状を , バ 道路を走っている自動車があります。この ウンディングボリューム (bounding volume , とき , あなたを構成するポリゴンと自動車 行えるということです。もちろんそのため 境界形状 ) と呼びます。この方法を用いる に , 球やといった比較的判定が容易な形 を構成するポリゴンとの総当たり判定は , と , 大きく 2 点のメリットが存在します。 状を用います。低コストで当たりそうもな どう考えても必要なさそうです。別の例を まず 1 点目は , 「建物に当たらない限り , い状況を切り捨てられ , 必要なときだけ正 あげてみましよう。あなたがこうしている 確なチェックを行うこの方法は , 最適化と 外からはあなたに当たれない」 , 言い換え 間にも , 月は地球の周りを回っていて , 地 球は太陽を中心に移動しています。さて , ると「あなたを構成するポリゴンとの当た して理想的です。 太陽を構成するポリゴンとあなたを構成す Fig. 1 バウンディングスフィア る・・・・・・もういいですね。 ( a ) 中心と半径で表現 前者の当たり判定が明らかに必要ない理 由として , 自動車はあなたに当たる前に建 物に当たるだろうとか , あなたが高速道路 の塀を越えない限り自動車に当たらないだ ろうという空間的な関係が明確なことがあ げられます。一方後者は , 「太陽から見れ ばあなたは点での判定で十分だ」といった ような極端なサイズの差が , ポリゴンでの 総当たりを無意味なものにしているといえ ます。 はじめに ( b ) 球で表現するにはムダの多い形状 Enter The 3D Programming 101

8. 月刊 C MAGAZINE 2001年9月号

Java programmingTips 松浦健一郎 ( ひぐべん工房 ) 第 14 回 Java NativeInterface (JNI) その 2 今回は前回に引き続き , JN について解説します。 JNI& は , Java プログラムとプラットホーム依存のネ イティブプログラムの間を接続するインタフェイスです。今回は JNI を用いて , Java のオブジェクトや配 列を , Java プログラムとネイティブプログラムとの間でやりとりする方法を解説します。またその応用と して , 前回作成した簡易 CD プレイヤーの機能を拡張します。 それではコンパイル方法を説明します。 ndard Edition, Ver. 1.3.0 ( 以下 JDKI. 3 ) を使 Java プログラムーネイティブ 用しました。 プログラム間のデータ交換 手順 1 javac JNITest3. java 最初にコマンドプロンプト ( または DOS 前回 , Java プログラムからネイテイププ 手順 2 ログラムに対して引数で文字列 ( String ) を プロンプト ) で以下のコマンドを実行して , 渡し , ネイテイププログラムの中で表示す Java プログラム (List 1 ) をコンパイルしま 次に JDKI. 3 の中の javah というツール を用いて , ヘッダファイル ( 付録 CD - ROM るプログラムの例を説明しました。また , す。 に収録の「 JNITest3. h 」 ) を生成します。 今回 , すべての Java プログラムのコンパ 逆に , ネイテイププログラムの中で文字列 を生成し , Java プログラムに返す方法も解 イルと実行に Windows 用の Java2 SDKSta javah -jni JNITest3 説しました。実際のアプリケーションでは , オプジェクト・配列の受け渡しの例 ( Java プログラム , JNITest3. java) 文字列だけではなく , さまざまなデータを Java プログラムとネイテイププログラムの 間でやりとりする必要があります。 JNI には , このようなデータ交換のため の仕組みがあります。今回はとくに Java プログラムにおけるオプジェクトの各フィ ールド ( メンノヾ変数 ) にアクセスする方法や , 配列データを読み書きする方法を中心に解 説します。 トオブジェクトや配列の受け渡し ListI, 2 は , Java プログラム←ネイティ ププログラム間でオプジェクトや配列を受 け渡しするプログラムの例です。 Java プロ グラム側で定義したオプジェクトや配列 を , C プログラム側で読み書きします。具 体的には , Java プログラムが初期化したオ プジェクトや配列の値を , C プログラムが 読み出して表示します。続いて C プログラ ムがオプジェクトや配列の値を変更し , Ja va プログラムに戻って , 変更後の値を Java プログラムが表示します。 1 26 C MAGAZINE 2001 9 List import java. awt.*; - I のテスト ( オブジェクトや配列の受け渡し ) public class JNITest3 { / / int 型 土 n し a ー / / char 型、 static static char b ー 〃 do 面厄型配列 dO cl ーネイティブメソッドの宣言 public native vo su わ ( 加 0 0 - DLL のロード stat ic { $ystem.loadLibrary("JNITest3Ext"); メインルーチン public static VOid main(String[ ] args) new JNITest3( - コンストラクタ public JNITest3( ) { - 変数の初期化 b 記・ c=new d0 曲 [ 2 c [ 0 ] = 0. c [ 1 ト 0. point p=new 印加 # は - ネイティブメソッドの呼び出し - 変更された変数値の表示 system. ou し printl n ( : a=n 十 a 十 Java , b = ”十 b 十 c [ 0 ] = ″十 c [ 0 ] 十 % c [ 1 ト″十 c [ 1 ] + ー P = ( ” + P. x 十 % ″十 P. Y 十つ″

9. 月刊 C MAGAZINE 2001年9月号

XML ドキュメントの各要素に対する操作を 次の個人工レメントは少し複雑になって 定されていません。 SQL で行うことができ , 各要素に注目した います。まず , 個人工レメントにはアトリ それでは , XML ドキュメントのパースを 続けましよう。次は個人工レメントの子要 更新や参照などについては XML ドキュメン ビュートとして名前属性が存在します。そ 素である住所エレメントです。住所エレメ トを意識せずに行うことが可能です。この こで , アトリビュート ID に名前属性の ID で 方法は , もともと表形式で表現できる , ど ある " 4 " が指定されています。また , 個人工 ントもその内容であるテキスト要素が存在 ちらかといえば平坦な構造をした XML ドキ しています。 ID " 7 " で存在するレコードがそ レメントの子要素として複数の要素が存在 ュメントを扱う場合には有効ですが , 階層 していますが , その中で最初に登場する要 れです。そのため , 住所エレメントの子要 素 ID に " 7 " を指定しています。また , 住所工 が深く複雑な構造を持つ XML ドキュメント 素である住所エレメントの ID である " 6 " が子 要素 ID として指定されています。 レメントには SibIing ( 兄弟 ) 要素として TEL, を格納しようとすると , テープル間の関係 が複雑になり , テープルを結合するときの さて , まずはアトリビュートのほうから コメントの各要素が存在しています。その 実行効率の低下や , 正規化をともなう表形 解決しましようか。個人工レメントのアト 中から次に登場する要素として旺 L エレメ リビュートとして存在する名前アトリビュ 式への変換コストが問題になってきます。 ントの ID である " 8 " が次要素 ID に指定され また XML ドキュメントとしてデータを取 ートには , アトリビュートの内容であるテ ています。残りも同じように処理していく り出す場合の , 各要素を取り出して XML ド キスト要素が存在します。これも立派な要 と Fig. 2 ができあがります。 キュメントを再構築する際に発生するコス 素なので , 1 つのレコードとして格納され このようにして RDB に格納すると , テー ています。この ID は " 5 " なので , 名前アトリ プルのリレーションが複雑になってしまう トも考慮する必要があります。さらに XM L ドキュメントの構造が変更になった場合 ビュートの子要素 ID に " 5 " が指定されていま ような XML ドキュメントでも格納できるし , に , SQL を利用してアクセスを行っている す。名前アトリビュートのテキストエレメ XML ドキュメントの構造に依存しない形で 部分について , プログラムの変更が必要に ントは子要素もアトリビュートも持ってい 格納できるというメリットがあります。し なる可能性があります。こうなると XML の ないため , これらのフィールドには何も指 かし , この方法で格納した XML ドキュメン 特徴の 1 つである構造の変化に柔軟に対応 Fig. 2 レコードとして展開する方法 できるという利点が生かしきれません。 <?xml version= 1 0 > レコードとして展開する方法 く住所録 > く個人名前 = 喉小路俺麻呂ゝ この考え方をもう 1 歩進めた方法として , く住所 > 大阪市新宿区く / 住所 > XML ドキュメントの各要素を分解し , その く TEL > 999-8888 く几 EL > くコメント > 旧華族でおじゃるく / コメント > 構造に従って 1 要素 1 レコードとして RDB に く / 個人 > 格納する方法も考えられています ( Fig. 2 ) 。 く / 住所録 > これについては , どのように変換されて いるか説明が必要でしよう ( 自分でも Fig. 2 を作っているときにわけがわからなくなり ました ) 。 基本的に各要素を表すレコードに一意の ID を付与し , その ID の関連によって XML ド キュメントの構造を表しています。まず最 初にルート要素としてドキュメントという タイプの要素があります。この子要素とし て次のレコードの住所録エレメントがある ので , ドキュメントの子要素 ID に住所録工 レメントの ID である " 2 " を指定します。住 所録エレメントの下には個人工レメントが 存在しています。先と同様に住所録エレメ ントの子要素 ID に個人工レメントの ID であ る " 3 " を指定します。 24 C MAGAZINE 2 開 1 9 アトリビュート ID 子要素 ID 次要素 ID タイプ 1 ドキュメント 住所録 2 エレメント 個人 3 エレメント 4 アトリビュート 名前 5 テキスト 僕小路俺麻呂 6 エレメント 住所 7 テキスト 大阪市新宿区 8 エレメント TEL 9 テキスト 999-8888 10 エレメント コメント 1 1 テキスト 旧華族でおじゃる ID っ 4 っ 0 CD ) 8 7 1 0 9

10. 月刊 C MAGAZINE 2001年9月号

バウンディングスフィアの作成方法 ( a ) x 方向と / 方向で最小 , 最大になる矩形を考 える ( b と B を通る円を描く ( c ) 半径を拡大しながら 点 C に向かって中心 も移動 4 102 C MAGAZINE 2001 9 たらなかったというむだ骨が増えてしまい しくボリゴンを調査してみたら , 結局は当 ります。これでは , 当たったかと思って詳 に , 球で表現するにはムダの多い形状があ きな状況も存在します。 Fig. 1- ( b ) のよう 長所ばかりではありません。やはり不向 による一刈りで不可視とできるのです。 います。自分の視界から外れた物体は , 球 て , クリッピング ( 可視判定 ) にも使われて また , 平面との判定が容易なのを生かし ィアは非常によく使われています。 との判定で相性のよいバウンディングスフ はほとんど光線追跡に費やさるので , 直線 などの分野です。レイトレーシングの計算 これが活躍するのは , レイトレーシング ことは , 前回紹介したとおりです。 いずれにしても基本的な当たり判定である られます。球同士 , 球と線分 , 球と平面の て , 球の取り扱いが便利だという点があげ このバウンディングスフィアの利点とし ig. l-(a))o ので , 中心と半径によって表現されます (F ng sphere, 境界球 ) です。文字どおり球な 初めはバウンディングスフィア (boundi バウンディングスフィア その生成の方法を見ていきます。 ームとして利用される各種形状の特徴と , こでは , これらバウンディングボリュ ます。 ることで , 円あるいは球の作成が可能にな 1 回 , 合わせて 2 回 , すべての頂点を走査す る手順で 1 回 , 外側の点を発見する手順で 作成することができます。最大最小を求め このようにして , すべての点を含む円を む円を得ることができます ( Fig. 2- ( c ) ) 。 拡大します。すると , 点 C と前回の円を含 の半分だけ移動して , 後ろ半分だけ半径を 中心も移動させます。はみ出していた距離 大するのですが , 同時に , 点 C に向かって きいことに気づきます。そこで , 半径を拡 ある , つまり中心からの距離が半径より大 ところがこのとき , 点 C はこの円の外側に に A と B を通る円を描きます ( Fig. 2- ( b ) ) 。 B との中間点をとります。この点 x を中心 準として採用します ( Fig. 2-(a))0 次に A と x 方向で最小最大を提供した点 , スと B を基 方向で長さが最大となっているので , この なるような矩形を考えます。この矩形は x れらのうち , x 方向と方向で最小最大に 平面に頂点が 5 点存在するとします。 じ手順で生成を行うことができます。 上で行いますが , 三次元上でもまったく同 すい作成方法を紹介します。説明は二次元 こでは一例として , 比較的理解のしや ほどコストの高い難問なのです。 を求める問題は , それが 1 つの研究になる ない形状です。というのも , 最小の外接球 さらに動的な生成にはあまり向いてい Fig. 3 AA バウンディングボックス 後述するとして生成の方法を見てみましょ あるということです。当たり判定の方法は クがしやすいということと , 生成が簡単で この形状の利点は , 当たり判定のチェッ 小点〃 . と最大点。の 2 点で表現されます。 半径で表現されましたが , この矩形は , 最 た形でが描かれています。球は中心点と BB です。見た目どおり , x 軸 , 軸に沿っ Fig. 3 を見てください。太線の矩形が AA 沿った , といった意味の言葉です。 ろに特徴があります。これは , 各軸方向に は籀なのですが , Axis-Aligned というとこ があります。名前がボックスというからに ed bounding box , 以下 AABB) というもの AA バウンディングボックス (Axis-Align AA バウンティングボックス ず用いられている形状です。 は魅力的です。ゲームなどの分野では , 必 ングスフィアの当たり判定のコストの安さ 問題はいくつかあるにせよ , バウンディ 算量は増大することになります。 最高な位置関係を保つ必要があるので , 計 頂点の位置を的確に求め , すべての点との とした理想的な円が考えられそうですが , 一目見てわかるように , もっとピッタリ 法です。 ります。これは計算量の面では効果的な方