最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

javascript - How to get name of child constructor? - Stack Overflow

programmeradmin1浏览0评论

I have a class with prototype method printConstructorName which prints the name of the constructor:

function Parent(){
}

Parent.prototype.printConstructorName = function(){
   console.log(this.constructor.name);
};

var parent = new Parent();
parent.printConstructorName(); // It gets 'Parent'.

A class Child inherits the Parent through the prototype:

function Child()
{
}

Child.prototype = Parent.prototype;

var child = new Child();
child.printConstructorName(); // It gets 'Parent', but 'Child' is necessary.

How to get the name of Child's constructor through the Parent's prototype method?

I have a class with prototype method printConstructorName which prints the name of the constructor:

function Parent(){
}

Parent.prototype.printConstructorName = function(){
   console.log(this.constructor.name);
};

var parent = new Parent();
parent.printConstructorName(); // It gets 'Parent'.

A class Child inherits the Parent through the prototype:

function Child()
{
}

Child.prototype = Parent.prototype;

var child = new Child();
child.printConstructorName(); // It gets 'Parent', but 'Child' is necessary.

How to get the name of Child's constructor through the Parent's prototype method?

Share Improve this question asked May 7, 2013 at 14:40 Denis KreshikhinDenis Kreshikhin 9,4409 gold badges55 silver badges85 bronze badges 1
  • 2 Please notice that name is a non-standard property of functions and should not be used for anything else than debugging. – Bergi Commented May 7, 2013 at 14:46
Add a ment  | 

6 Answers 6

Reset to default 4

Working fiddle

The inheritance pattern is the problem. Here's the quick fix:

function inherits(childCtor, parentCtor) {
  function tempCtor() {};
  tempCtor.prototype = parentCtor.prototype;
  childCtor.prototype = new tempCtor();
  childCtor.prototype.constructor = childCtor;
};

function Parent(){}

Parent.prototype.printConstructorName = function(){
   return this.constructor.name;
};

var parent = new Parent();
console.log(parent.printConstructorName()); // It gets 'Parent'.

function Child() {
    Parent.call(this);
};
inherits(Child, Parent);

var child = new Child();
console.log(child.printConstructorName()); // It gets 'Child'.

You are assigning the Parents prototype object to Child.prototype - which means that every child instance inherits from the same thing as all parent instances, and of course they inherit the same constructor property that way.

Instead, create a new object for the Child.prototype, inheriting from the Parent.prototype, and you can overwrite the constructor property then:

Child.prototype = Object.create(Parent.prototype, {
    constructor: {value: Child, configurable: true}
});

Your inheritance mechanism is clearly wrong. The way you've done it, if you add a property to Child.prototype, all Parent objects will also get it...

You might want an inherit function something like this:

inherit = (function() {
    function F() {};
    return function(parent, child) {
        F.prototype = parent.prototype;
        child.prototype = new F();
        child.prototype.constructor = child;
    };
}());

which you can then use this way:

function Parent() {
}

Parent.prototype.printConstructorName = function(){
   console.log(this.constructor.name);
};

var parent = new Parent();
parent.printConstructorName();  // Parent

function Child() {
}

inherit(Parent, Child);

var child = new Child(); // Child
child.printConstructorName();

When you're extending an existing constructor, you should set the child prototype to an instance of the parent class, so that changes to the child prototype don't affect the parent prototype.

Then you can simply override the constructor such that it points to the correct function.

function Parent() {
    ....code...
}

Parent.prototype.printConstructorName = function () {
    console.log(this.constructor.name);
};

function Child() {
    ...code...
}

Child.prototype = new Parent();
Child.prototype.constructor = Child;

p = new Parent();
p.printConstructorName(); //Parent

c = new Child();
c.printConstructorName(); //Child

Write an extend function, something like:

__extend = function(child, sup) {
    for (prop in sup.prototype) {
        child.prototype[prop] = sup.prototype[prop];
    };
};

And then you call it instead of doing the prototype = new parent trick - like:

var Parent = function() {}
Parent.prototype.name = function() { return "name" };

var Child = function() {}
__extend(Child, Parent);

Check out this fiddle: http://jsfiddle/Cmg4A/

Maybe you should override the printConstructorName in Child :D.

发布评论

评论列表(0)

  1. 暂无评论