2006-01-10
■[JSON]JSONの書き方について考えてみた・1
連休中にJSONの書き方についていろいろ考えてみたので、まとめてみたいと思います。
基本
JSONについての基本的なことは他サイトに任せるとして、、簡単にいうとJavaScriptの書式を利用したデータ記述フォーマットです。
基本的にはこのようなテキストファイルを用意して、
[ 'text', 'hoge', 'fuga' ];
XMLHttpRequestなどで取得し、次のようにして利用します。(取得したテキストデータはjsonTextに入っているとする)
var jsonData = eval(jsonText);
これで、jsonDataは['text','hoge','fuga']の配列になります。
ちなみに、
eval('var jsonData = ' + jsonText);
とすることもあります。この2つには違いがあり、
var a = eval('var b = ' + '1; 2; 3;');
の場合、aに3、bに1が入ります。evalの戻り値には最後の評価値が入り、evalの引数のテキストにつなげた場合は最初の評価値が入ります。評価値がひとつならば当然どちらも同じになります。
外部ドメインから読める形式
JSONの特徴として、JavaScriptの書式で作られているということがあげられますが、これをうまく利用するとドメインを超えたAjaxが実現できます。
jsonData = [ 'text', 'hoge', 'fuga' ];
しかし、このままだとグローバルの名前空間を侵食してしまうので、オブジェクトをひとつ用意してその中にデータを入れることがあります。
if (typeof(Hoge) == 'undefined') Hoge = {}; Hoge.data = [/* 略 */];
このようなJSONデータをscriptエレメントを利用して読み込んで利用します。
DOMを利用して動的にscriptエレメントを作成すれば、動的に読み込むこともできます。この場合、読み込みが終了したことを知らせるためにコールバックの仕組みを組み込む場合もあります。
if (typeof(Hoge) == 'undefined') Hoge = {}; Hoge.data = [/* 略 */]; if (typeof(Hoge.onload) == 'function') { Hoge.onload(Hoge.data); }
この場合、scriptエレメントの生成前にHoge.onloadに任意の関数を仕込んでおくと読み込み完了時に呼ばれます。
オブジェクトの生成やコールバックをデータ部の前後に組み込むと、最初・最後の評価値が変わるので、Ajaxでテキストを読み込んだ場合も
var data = eval(jsonText); eval('var data = 'jsonText);
といったデータの取得方法が使えなくなり、直接Hoge.dataにアクセスするなどの方法に変える必要が出てきます。
応用・追加対応型
ネタ元はこちら。最速インターフェース研究会 :: Ajaxを使ったシンプルなチャット
if (typeof(Hoge) == 'undefined') Hoge = {}; Hoge.data = []; var count = 0; Hoge.data[count++] = 'text'; Hoge.data[count++] = 'hoge'; Hoge.data[count++] = 'fuga';
データの追加が追加書き込みでできる*1ので、静的なファイルに随時追加していく場合に便利。ちなみに、現在のGA-BBSでも同様の方式です。
常に0から順番につめていくのであれば、こういった方法もできます。
if (typeof(Hoge) == 'undefined') Hoge = {}; Hoge.data = []; Hoge.data.push('text'); Hoge.data.push('hoge'); Hoge.data.push('fuga');
しかし、ファイルの最後がデータの追加になるので、読み込み完了時のコールバックの仕組みが書けず、外部ドメインから利用するときにちょっと不便です。
続く
*1:ファイルの最後にデータを追加するので、データの挿入位置を探す必要がない。そもそもファイルの中身を読み込む必要すらない。