Javascript:[user-defined prototype]中的变量不可用

Javascript:[user-defined prototype]中的变量不可用,javascript,prototype-programming,inheritance,Javascript,Prototype Programming,Inheritance,我在《面向Web开发人员的专业javascript》一书中使用javascript。我在第6.2.6节中练习了一个示例。代码如下所示: function creatPrototype(subType, superType) { function subTypePrototype(){}; subTypePrototype.prototype = superType.prototype; subTypePrototype.constructor = subType;

我在《面向Web开发人员的专业javascript》一书中使用javascript。我在第6.2.6节中练习了一个示例。代码如下所示:

function creatPrototype(subType, superType) 
{
    function subTypePrototype(){};
    subTypePrototype.prototype = superType.prototype;
    subTypePrototype.constructor = subType;
    subTypePrototype.str = "say";
    return new subTypePrototype();
}

function Person(name, age) 
{
    this.name = name;
    this.age = age;
}
Person.prototype.say = function(){
    writeln("bill say");
}


function itMan(name, age){
    Person.apply(this, arguments); 
}
itMan.prototype = creatPrototype(itMan, Person); 


var Bill = new itMan("bill", 25);

writeln(itMan.prototype.str);    //expect "say"
writeln(Person.prototype == itMan.prototype.prototype);   //expect true
Bill.say();  //expect "bill say"
结果是:

未定义

假的

比尔说

为什么?

  • itMan.prototype.str应该“说”

  • Person.prototype和itMan.prototype.prototype应该指向同一个对象

  • Bill.say()正确运行,这样原型链就可以了


  • 代码有一些错误,请尝试此代码

    function creatPrototype(subType, superType) 
    {
        function subTypePrototype(){
        this.prototype = superType.prototype;
        this.constructor = subType;
        this.str = "say";
    }
    
    
        return new subTypePrototype();
    }
    
    function Person(name, age) 
    {
        this.name = name;
        this.age = age;
    }
    Person.prototype.say = function(){
        document.writeln("bill say");
    }
    
    
    function itMan(name, age){
        Person.apply(this, arguments); 
    }
    itMan.prototype = creatPrototype(itMan, Person); 
    
    
    var Bill = new itMan("bill", 25);
    
    document.writeln(itMan.prototype.str);    //expect "say"
    
    document.writeln(Person.prototype == itMan.prototype.prototype);   //expect true
    Bill.prototype.say();  //expect "bill say"
    
    在您的代码中,您没有使用
    对象,因此
    itMAn
    没有变量str, 你用的是
    subType.constructor=子类型
    subtype.prototype=superType.prototype
    
    因此,
    Bill.say
    起作用,而
    Person.prototype==itMan.prototype.prototype
    不起作用。

    prototype是一个保留关键字,使用时必须非常小心

    您的代码中有几个问题

    然后在CreateSubtoType中:

    return new subTypePrototype();
    
    您正在创建一个函数,然后返回已执行的函数结果,其中应该返回指向函数的指针,如

    return subTypePrototype;
    
    但您不应创建函数,因为您似乎希望检索父“原型”:

    因此,您的代码应该更像:

    function createPrototype(subType, superType) 
    {
      subTypePrototype = superType.prototype;
      subTypePrototype.constructor = subType; //- beware this is wrong !!!
      subTypePrototype.str = "say";
      return subTypePrototype;
    }
    
    检查我标记为错误的行,这样做是在更新子类型和父类型

    如何做到:
    也就是说,如果你想扩展一个对象,我建议你使用现有的libs。(jQuery、Mootools等)

    您必须考虑哪个属性属于构造函数,哪个属性属于实例
    prototype
    是函数的一个属性,但是
    constructor
    str
    应该都是实例的属性

    这应该做到:

    function createPrototype(subType, superType) 
    {
        function subTypePrototype(){};
        subTypePrototype.prototype = superType.prototype;
    
        var newPrototype = new subTypePrototype();
    
        newPrototype.constructor = subType;
        newPrototype.str = "say";
        return newPrototype;
    }
    
    但是,由于您也是passong
    子类型
    ,您实际上可以直接分配原型:

    function inherit(subType, superType) 
    {
        function tconstr(){};
        tconstr.prototype = superType.prototype;
    
        subType.prototype = new tconstr();
    
        subType.prototype.constructor = subType;
        subType.prototype.str = "say";
    }
    
    然后再打电话给我

    inherits(itMan, Person);
    

    Person.prototype和itMan.prototype.prototype应该指向同一个对象

    请记住,
    prototype
    函数的属性,而不是对象的属性。但是原型是一个对象。除非明确引用对象原型,否则无法访问它(但我不会这样做)

    使用ECMAScript 5,有一种方法可以使用获取原型。但这只适用于较新的浏览器


    这是你的一段代码。

    所以,你告诉他不要使用prototype,而你的链接是关于如何使用prototype关键字的文章?使用原型没有错;事实上,这是实现javascript继承的正确方法(至少Douglas Crockford说)。我不得不让你失望,但是
    prototype
    不是保留关键字:你的
    createprototype
    也不正确。分配给
    子原型的任何属性也将分配给
    超类型.prototype
    。这不是一个好方法。@RoccoC5:谢谢你指出这一点。你是对的,我写这篇文章可能太快了,而且我的英语不是那么正确。我已经相应地更新了帖子。@Felix:据我所知,这是因为如果你在类上计算自己的原型内容,我怀疑这个对象是否能正常工作。。。但无论如何,如果我错了,请纠正我。当然,我的示例是不正确的,但它只是为了解释这种方式的函数使用效率不高。然后,我使用链接提供了更深入的示例。您的方法更好,但将
    原型
    构造函数
    分配给
    是错误的。Felix在这方面是正确的,这是一个示例,演示了如何正确操作。@Felix thanx指出,您是正确的,您的方法是正确的,您得到了要点。您的解决方案与本书中的原始示例类似。SubsubPrototype.constructor和str不能是返回值new SubsubPrototype()的一部分。