Hatena::Groupjavascript

JavaScriptで遊ぶよ

 | 

2010-05-21

JavaScript のクラス・名前空間の定義方法

07:40

とても素晴しい記事を見つけました。

JavaScript はクラス定義の方法とかが Ruby みたいにちゃんとした記法が無いから、他人のコードを読むとまず「どこからどこまでがクラスか」とかを考えないといけないんですよね。

個人的にはこのあたりが、サーバーサイド JavaScript がおすすめできないところだと思います。(僕が Node.js が好きで書いてますが)


というわけで、みんなどうやってクラスとか名前空間的なオブジェクトを書いてるのか知りたいので、自分も一票投じてみます。(prefix 使いたくないとか前提条件が示されていますが、とりあえずあまりそれに拘らない方向でいきます)

示されている b の方法に近いですが、最近はこんな感じで書いています。

var myObject; // とりあえず外側に名前空間オブジェクトを定義

(function myObjectClosure() { // ← IE 無視の場合は名前を付ける

var private = 'private'; // プライベート変数
var func = function func() {}; // プライベート関数

myObject.public = 'public'; // パブリック変数
myObject.method = function myObject_method() {}; // パブリック関数

function func2 (){} // プライベート関数その2 (ユーティリティー色の強いものはこのスコープの一番下に、Function Statement として書くことが多い)

}());

最後に、CommonJS の exports を使う場合は単純に myObject をエクスポートします。

exports.myObject = myObject;

利点や欠点は、元の記事の b (古典) のところに書かれている利点や欠点がほぼそのままあてはまります。他には、何が外側に出てくるのか見えやすいです。あと、こじつけっぽいですが、全体をまた別の関数で囲うと myObject もプライベートになってくれます (などと書くときは考えますが、実際にそんなことをしたことはありません)。

パブリック変数や関数にイチイチ myObject とか書かないといけないのはやっぱり面倒ですね。

パブリック変数を外側には見えるようにするけど書き換えられることを想定しない場合 (主に自分しかユーザーがいない場合) は var method = myObject.method として内部で使うこともあります。

名前空間内は、上から読んで分かりやすいと思う順番で書きます。プライベート変数を一番上で全部定義したりせずに、それが使われている関数の直前に書きます。

プライベート関数の中でもユーティリティー系のもの ($X とか) は下のほうに書きます。

関数に名前を付けるようにするのは uupaa さんの「ナビ子記法」を見て以来積極的にやっています。

ただし、IE では Function Expression に関数名を付けると外のスコープに漏れちゃうので使いません。2つの関数オブジェクトが定義されてしまったり、メモリリークの可能性を考えるのも面倒なので。

with を使うのは、個人的には敬遠します。strict モードでは使えなくなりますし。withevalJavaScript から追い出したい、みたいなことを Crockford さんも言ってましたし。

トラックバック - http://javascript.g.hatena.ne.jp/edvakf/20100521
 |