JS Синтаксис класса ES6 и путаница с прототипами - PullRequest
1 голос
/ 28 апреля 2020

хорошо, насколько мне известно, мы бы написали конструктор класса, например,

class User {
    constructor(name, age) {
        this.name = name;
        this.age = age;
    }

    //anything outside of constructor belong to this.prototype

    getName() {
        console.log(this.name);
    }
    getAge() {
        console.log(this.age);
    }
}

, поэтому вместо этого я напишу что-то вроде этого:

class User {
    constructor(name, age) {
        this.name = name;
        this.age = age;
    }

    getName() {
        console.log(this.name);
    }
}

User.prototype.getAge = function () {
    console.log(this.age);
};

Технически это должно быть точно так же правильно? Или я не прав? потому что, когда я попробовал это, каждый из которых, я получаю 2 разных результата:

let user = new User('john', 23);

let properties = [];

for (let prop in user) {
    properties.push(prop);
}

console.log(properties); //The first code result : ["name", "age"]
                         //The second code result : ["name", "age", "getAge"]

Так в чем же разница между ними?

Ответы [ 3 ]

0 голосов
/ 28 апреля 2020

Во втором случае вы добавляете свойство с именем getAge. И его тип является функцией.

0 голосов
/ 28 апреля 2020

Разница между ними заключается в том, что использование User.prototype.getAge = ... добавит свойство с дескриптором свойства enumerable: true. Это означает, что он отображается в for...in циклах.

Оператор for...in выполняет итерации по всем перечисляемым перечислимым свойствам объекта, для которого заданы строки (игнорируя те, которые обозначены символом с), , включая унаследованные перечисляемые свойства .

class User {
    constructor(name, age) {
        this.name = name;
        this.age = age;
    }

    getName() {
        console.log(this.name);
    }
}

User.prototype.getAge = function () {
    console.log(this.age);
};

let user = new User('john', 23);
let properties = [];

for (let prop in user) {
    properties.push(prop);
}

console.log(properties);

console.log(Object.getOwnPropertyDescriptor(User.prototype, "getName"));
console.log(Object.getOwnPropertyDescriptor(User.prototype, "getAge"));

Если вы хотите точно определить прототип таким же образом, вам придется использовать тот же дескриптор свойства. Это может быть достигнуто с помощью Object.defineProperty():

Object.defineProperty(User.prototype, "getAge", {
    value: function () {
        console.log(this.age);
    },
    writable: true,
    enumerable: false,
    configurable: true,
});
0 голосов
/ 28 апреля 2020

Синтаксис класса - только sytacti c sugar.

...