web-dev-qa-db-ja.com

Javascript-オブジェクトに関数を保存する-悪い習慣ですか?

関数を定義するだけでなく(したがってグローバルに)オブジェクトに関数を格納することは、コーディングの慣行として不適切と見なされますか?

考慮してください:

1。

_Foo = {
    bar: function() {
        alert("baz");
    }   
}
_

Foo.bar();

vs.

2。

_function bar() {
    alert("baz");
}
_

bar();

確かに、2番目の例のコードはわずかに少ないかもしれませんが、多くの関数を取得し始めると、面倒になります。たとえば、updateGame()を使用する代わりにGame.update()を使用する方が、ずっときれいです。または類似。 Game.notify.admin(id)などのようにさらに深くなると、さらにきれいなコードが得られます。

関数をオブジェクトに格納することによるマイナス面はありますか?

69
Zar

最初のアプローチが推奨されます。この方法では、グローバルスコープを汚染するのではなく、関数のスコープを明示的に定義しています。最初のアプローチを使用することの欠点はありません。唯一の利点:-)

結論:関数を定義するには、常に最初のアプローチを使用してください。 2つ目は90年代のjavascriptのようなものです。過去に戻って安らかに置いておき、適切なスコープを使用しましょう。

68
Darin Dimitrov

名前空間オブジェクトには魔法はありません。また、多くのグローバル変数を使用する場合、必ずしも問題は発生しません。 「名前空間」オブジェクトを使用する主な理由は、グローバル変数名が重複する可能性を減らすためです。 2番目の理由は、便宜上、同様の機能をグループ化することです:

// Object example (suggested best practice):
// DOM functions are under myLib.dom
myLib.dom.someDOMFunction0;
myLib.dom.someDOMFunction1;

// Utility functions are under myLib.util
myLib.util.someUtilityFunction0;
myLib.util.someUtilityFunction1;

上記は、同様のグローバル変数と重複する可能性が実質的に同じであることに注意してください。

// Global variable example:
myLib_dom_someDOMFunction0;
myLib_dom_someDOMFunction1;

myLib_util_someUtilityFunction0;
myLib_util_someUtilityFunction1;

もちろん、前者の方が作業しやすいと思われるため、一般的に好まれます。 2番目のアプローチ(私は最初のアプローチを使用)を採用することを推奨していません。多くのグローバル変数の作成に問題があるが、いわゆる「グローバル名前空間汚染」は危険として非常に過大評価されています。

4
RobG

この特定のケースでは、最初のケースに進みます。しかし、Fooオブジェクトが本当に複雑になる場合は、コンストラクターを使用する機会を与える別のアプローチを使用することをお勧めします。また、関数のスコープに関しては、最初のアプローチが最適でない場合があります。

function Foo(appName){
    this.name = appName;      
}

Foo.prototype.Bar = function(){
   alert(this.name)
}

var a = new Foo("baz");
a.Bar();
3
Karl Mendes