定义类的最佳方式是什么?我知道这在大多数情况下是你喜欢使用的选项,但这三个例子之间的直接区别是什么?
示例1
var Class = (function(){
function Class() {
this.test = 'test'
}
return Class;
})();
var c = new Class();
console.log(typeof Class);
console.log(c.test);
示例2
var Class2 = function(){
this.test = 'test'
};
var c2 = new Class2();
console.log(typeof Class2);
console.log(c2.test);
示例3
function Class3(){
this.test = 'test'
};
var c3 = new Class3();
console.log(typeof Class3);
console.log(c3.test);
有时我也这样使用它:var类=(function(){var Private={},Public={};
Private._doSomething = function() {
// something
}
Public.doSomethingElse = function() {
// something else
}
return Public;
})();
注意:下面的主要答案写在2012年。有关JavaScript自己的class
功能(ES2015+)的其他注释,请参见末尾。
"最佳"本质上是一个主观的东西,但我会尝试指出每一个的一些信息,让你自己决定"最佳">
示例1
为您提供了一个方便的范围(匿名函数),您可以在其中放置只有Class
函数才能访问的真正私有的类范围信息(和实用程序函数):
var Class = (function(){
var trulyPrivateInformation = 42;
function trulyPrivateUtilityFunction() {
// ...
}
function Class() {
this.test = 'test';
}
return Class;
})();
示例1不是"提升"的。它是作为逐步代码的一部分进行处理的。
Class
函数将具有真实名称。
示例2
创建一个没有名称的函数,并将其分配给一个有名称的变量。现代浏览器对此非常聪明,但至少在理论上,该功能是匿名的,这会影响您的工具可以为您提供的信息(截至ES2015)有一个名称(Class2
),但在IE等过时环境中除外。它没有示例1所具有的私有类范围。
与示例1一样,示例2是作为分步代码的一部分进行处理的,而不是提升的。
示例3
只是示例1,没有私有类范围,但它也被"吊起来"—CCD_ 5函数是在执行任何逐步代码之前定义的。这意味着这是有效的:
var c = new Class();
console.log(c.test); // Logs 'test'
function Class() {
this.test = 'test';
}
请注意,即使Class
是向下定义的,它也是在运行上述代码之前完成的。实施例1或实施例2都不是这样。
与示例1(但不是示例2)一样,Class
函数具有真实名称。
2015年,JavaScript有了自己的class
语法。在2019年,所有现代浏览器都支持它,如果你需要支持IE,你可以使用Babel等工具进行转换。以下是class
与OP的问题的关系:
class
的示例1
const Class = (() => {
let trulyPrivateInformation = 42;
function trulyPrivateUtilityFunction() {
// ...
}
return class Class {
constructor() {
this.test = 'test';
}
}
})();
在代码的逐步执行中处理的。具有真正私有的作用域(在匿名作用域函数内),用于真正私有的内容。有一个合适的名字。
具有class
的实施例2(也是具有class
的实施例3)
class Class2 {
constructor() {
this.test = 'test';
}
}
let c2 = new Class2();
console.log(typeof Class2);
console.log(c2.test);
在代码的逐步执行中处理的。没有示例1所具有的真正私有的作用域(尽管私有字段和方法很快就会出现)。有一个合适的名字。