JavaScriptで変数といえば「var」ですが、使用する変数が増えてくると取り扱いが面倒になってきます。
配列などで管理する方法もありますが、一長一短あるかと思います。
そこで、上手い方法はないかと模索していて辿り着いたのが、データオブジェクト風に扱う方法でした。
早速、例として、「名前」、「生年月日」、「年齢」という属性を持つ「人物」というデータオブジェクトを定義してみます。
/** 人物 */
function Person() {
/** 名前 */
var name = "";
/** 生年月日 */
var birthday = "";
/** 年齢 */
var age = 0;
/** 名前を設定する。 */
this.setName = function (_name) {
name = _name;
}
/** 名前を返却する。 */
this.getName = function () {
return name;
}
/** 生年月日を設定する。 */
this.setBirthday = function (_birthday) {
birthday = _birthday;
}
/** 生年月日を返却する。 */
this.getBirthday = function () {
return birthday;
}
/** 年齢を設定する。 */
this.setAge = function (_age) {
age = _age;
}
/** 年齢を返却する。 */
this.getAge = function () {
return age;
}
}
|
prototypeを使って記述していく方法などもあるかと思いますが、本職がJavaなので、
慣れた手触りで使えたら楽ちんだなあという要求から、私は今回の方法に落ち着きました。
setter/getterを介して内部変数にアクセスする、一般的なデータオブジェクトです。
使う時は以下のように。
var person1 = new Person();
person1.setName("山田 太郎");
person1.setBirthday("03/01");
person1.setAge(30);
var person2 = new Person();
person2.setName("山田 一");
person2.setBirthday("08/06");
person2.setAge(8);
person1.getAge(); // 30
person2.getBirthday(); // 08/06
person1.getName(); // 山田 太郎
|
関数にパラメータとして渡すことも出来ますし、
/** 加齢 */
function AddAge(person) {
person.setAge(person.getAge() + 1);
}
AddAge(person2);
AddAge(person2);
person2.getAge(); // 10
|
なので、こういった使い方も出来ます。
/** 家族 */ function Family() { /** 父 */ var father = null; /** 母 */ var mother = null; /** 子供 */ var child = null; /** 父を設定する。 */ this.setFather = function (_father) { father = _father; } /** 父を返却する。 */ this.getFather = function () { return father; } /** 母を設定する。 */ this.setMother = function (_mother) { mother = _mother; } /** 母を返却する。 */ this.getMother = function () { return mother; } /** 子供を設定する。 */ this.setChild = function (_child) { child = _child; } |
「父」、「母」、「子供」という「人物」型の属性を持つ「家族」というデータオブジェクトを作りました。
var yamada = new Family();
yamada.setFather(person1);
yamada.setChild(person2);
yamada.getFather().getBirthday(); // 03/01
yamada.getChild().getName(); // 山田 一
|
クラスを継承して新しいクラスを作ることも出来ます。例えば、「家族」に「弟」を追加します。
/** 弟のいる家族 */
function BigFamily() {
Family.call(this);
/** 弟 */
var brother = null;
/** 弟を設定する。 */
this.setBrother = function (_brother) {
brother = _brother;
}
/** 弟を返却する。 */
this.getBrother = function () {
return brother;
}
}
var tanaka = new BigFamily();
var person3 = new Person();
person3.setName("田中 花子");
person3.setBirthday("04/04");
person3.setAge(29);
var person4 = new Person();
person4.setName("田中 次郎");
person4.setBirthday("12/23");
person4.setAge(6);
tanaka.setMother(person3);
tanaka.setBrother(person4);
tanaka.getMother().getName(); // 田中 花子
tanaka.getBrother().getName(); // 田中 次郎
|
Javaと違って変数の型の扱いが緩いので、取り扱いには注意しなければいけないのが難点でしょうか。
特に、パラメータで渡す場合など、コンパイルエラー等を出してくれる訳ではないので、
実際に実行される段になってようやくエラーで止まる…ということがよくあります。
パラメータで渡ってきたオブジェクトの型チェックを行いたい場合は、typeofやprototypeを用いて
型を確認するのが良いようです。
// 標準的なオブジェクトの場合はtypeofで
typeof(person3.getName()) == 'string'; // true
typeof(person3.getAge()) == 'string'; // false
typeof(person3.getAge()) == 'number'; // true
// 今回作ったようなオブジェクトはprototypeで
Person.prototype.isPrototypeOf(person3); // true
Person.prototype.isPrototypeOf(tanaka); // false
BigFamily.prototype.isPrototypeOf(tanaka); // true
|
作り込みバグには気をつけなければいけませんね。