Javascript中的类变量

alt*_*ter 23 javascript syntax

如何在Javascript中声明类变量.

function Person(){
    fname = "thisfname"; //What needs to be put here
 }
alert(Person.fname) //It should alert "thisFrame"
Run Code Online (Sandbox Code Playgroud)

我不想使用这种方法.

function Person(){

 }
Person.fname = "thisfname";
alert(Person.fname) //alerts "thisframe"
Run Code Online (Sandbox Code Playgroud)

BGe*_*sen 37

JavaScript没有其他人所说的类.通过原型设计解决了继承问题,原型设计实质上只是在新创建的对象上创建不可删除的属性引用.JavaScript还有简单数据对象的替代品,即对象文字.

JavaScript中"类"的变体应定义如下:

// I use function statements over variable declaration 
// when a constructor is involved.
function Person(name) {
    this.name = name;
}

// All instances of Person create reference methods to it's prototype.
// These references are not deletable (but they can be overwritten).
Person.prototype = {
    speak: function(){
        alert(this.name + ' says: "Hello world!"');
    }
};

var Mary = new Person('Mary');
Mary.speak(); // alerts 'Mary says: "Hello world!"'
Run Code Online (Sandbox Code Playgroud)

this引用总是指向的所有者function.如果您在Person没有new运营商的情况下进行呼叫,则所有者将成为全局范围(窗口).如果不使用此引用将属性分配给实例,则属性将简单地声明为变量.如果你不使用该var语句,那么这些声明将创建糟糕的全局变量!

更多关于这个

this如果要向当前实例添加属性,则在构造函数中使用引用非常重要.如果不使用this,只创建一个变量(与属性不同),如上所述,如果不使用var语句,则创建全局变量.

function Person(){
    name = 'Mary'
}
var p = new Person();
alert(p.name); // undefined, did not use 'this' to assign it to the instance.
alert(name); // 'Mary', boo, it created a global variable!
Run Code Online (Sandbox Code Playgroud)

用这个!

function Person(){
    this.name = 'Mary'
}
var p = new Person();
alert(p.name); // 'Mary', yay!
alert(name);   // undefined, yay!
Run Code Online (Sandbox Code Playgroud)

注意,除非您将它分配给原型并在函数构造函数中再次覆盖它以使其成为拥有的属性,否则通过函数构造函数分配给实例的任何内容都不能被禁止.

当您通过作为构造函数加倍的函数创建新实例时,实际上会发生以下情况.

pseudo code:

   copy Person.prototype as person
   invoke Person function on person
   return person
Run Code Online (Sandbox Code Playgroud)

实际上,当你创建一个类的实例时,这就是每种经典语言中发生的事情.但JavaScript的主要区别在于它没有封装在一个很好的Class语句中.最初JavaScript甚至没有函数构造函数,但后来又添加了,因为SUN要求他们希望JavaScript更像Java.

对象文字

对于只携带内部数据而没有方法的对象的函数构造函数的替代方法是对象文字.

var Mary = {
    firstName: 'Mary',
    lastName: 'Littlelamb'
};
Run Code Online (Sandbox Code Playgroud)

这是声明内部对象的首选方式,而不是:

// do not ever do this!
var Mary = new Object();
Mary.firstName = 'Mary';
Mary.lastName = 'Littlelamb';
Run Code Online (Sandbox Code Playgroud)

使用技能集中的对象文字,可以使用模块模式(通常用于单例)为内部数据对象创建工厂模式.

var createPerson = function(firstName, lastName){
    return {
        firstName: firstName,
        lastName: lastName
    }
}
var Mary = createPerson('Mary', 'Littlelamb');
Run Code Online (Sandbox Code Playgroud)

这实现了一些舒适的封装,但只能用于内部数据对象.

使用Object文字和JavaScript可以做的另一件事是委托,这应该是首选.

var personMethods = {
    speak: function(){
        alert(this.firstName + ' says: "Hello world!"');
    }
};

var Mary = {
    firstName: "Mary",
    lastName: "Littlelamb"
};

var Peter = {
    firstName: "Peter",
    lastName: "Crieswolf"
};

personMethods.speak.apply(Mary); // alerts 'Mary says: "Hello world!"'
personMethods.speak.apply(Peter); // alerts 'Peter says: "Hello world!"'
Run Code Online (Sandbox Code Playgroud)

为什么这应该是首选?因为它使您的对象保持微小和可读性,即使是原型引用也会占用内存,当使用继承和"子类化"时,您最终会得到具有大量未使用方法引用的子实例.授权总是更好.


aul*_*ron 10

您提到的方法是如何定义类变量,另一种方式(内部function Person)是定义实例属性.

function Person(name){
    this.name = name;
}
Person.specie = "Human";

alert(Person.specie) //alerts "Human", a class variable.

var john = new Person('John');
alert(john.name); //alerts "John", an object property.
Run Code Online (Sandbox Code Playgroud)

  • @Ivo一般来说,它被认为是一个阶级.不,上面的`Person`是一个"用于实例化对象的函数",如果你想更具体的话.再一次,我相信我们可以把它称为一个类,一般说来,你可以继续更具体,最终调用它**ECMA脚本内存指向要解析的脚本的指针(1)通过括号调用句法.(1):在新的javascript编译器的情况下执行.**.重点是,上面的回答并不是要误导和滥用术语,而是以简单的方式解释一些事情. (5认同)