需要Javascript基本澄清

时间:2013-12-17 09:38:53

标签: javascript

我对C#知之甚少,现在我已经开始使用JavaScript并且在理解基础知识方面遇到了一些问题。

这是我的代码示例:

function BaseFunc(x, y) {
    this.X = x;
    this.Y = y;
}

function DerivedFunc(x, y, z) {
    this.Z = z;
    BaseFunc.call(this, x, y);
}

DerivedFunc.prototype = new BaseFunc;   


 function Test() {
    var d = DerivedFunc(1, 2, 3);
    var b = new BaseFunc(4, 5);
    d.sayHello();
    b.sayHello();
}

DerivedFunc.prototype.sayHello = function () {
    alert("Result is: " + (this.X + this.Y + this.Z));
}

在上面的代码中,我试图进行继承。

一切看起来都很好,直到我到达BaseFunc.call(this, x, y);行,这一行应该调用基函数,但在这种情况下this的用途是什么。 只是为了满足方法call的签名,它是如何工作的?

第二个问题是,在javascript中我们可以动态添加任何内容, 在我的例子中,我添加了一个sayHello()属性并为其分配了一个匿名函数。 与DerivedFunc.prototype.sayHello类似,我是在向BaseFuncDerivedFunc添加属性/方法,因为它已添加到原型中,因此我应该将其添加到BaseFunc中。但是当我执行上面的代码时,我得到sayHello未定义的错误。

有人可以向我说明出了什么问题吗,谢谢?

2 个答案:

答案 0 :(得分:1)

  

一切看起来都很好,直到我到达BaseFunc.call(this,x,y);这一行应该调用基函数,但在这种情况下使用它是什么。

这是因为在BaseFunc的调用中,this具有与调用DerivedFunc时相同的值,因此行this.X = x;等等BaseFunc正在分配给正确的实例。 (调用函数设置this的特定值是函数的.call.apply方法的作用。)

  

但是当我执行上面的代码时,我得到的错误是,没有定义Hello。

如果您d.sayHello遇到麻烦,那是因为您错过了newd = DerivedFunc(1, 2, 3);运营商。由于DerivedFunc仅在作为函数调用而不是通过new调用时,没有任何返回值,d将为undefined


请注意,您进行继承的方式虽然很常见但却存在问题。主要问题在于:

DerivedFunc.prototype = new BaseFunc;

您正在尝试使用一个旨在创建实例的函数,并接受参数,以便创建DerivedFunc将分配给事物的原型实例。那么BaseFunc应该对缺少的论点做些什么呢?然后,再次将其称为 (来自DerivedFunc)以初始化实例。 BaseFunc正在履行双重职责。

以下是您如何更正,首先是冗长的版本:

function x() { }
x.prototype = BaseFunc.prototype;
DerivedFunc.prototype = new x;
DerivedFunc.prototype.constructor = DerivedFunc;

或者,如果您可以依赖ES5的Object.create

DerivedFunc.prototype = Object.create(BaseFunc.prototype);
DerivedFunc.prototype.constructor = DerivedFunc;

现在我们没有调用BaseFunc来创建原型,但我们仍然将其prototype对象作为DerivedFunc的{​​{1}}对象的基础原型。我们不再知道如何处理prototype的参数,并且BaseFunc仅以其被设计为被调用的方式调用:初始化单个实例,而不是原型。

当然,不是每次我们想要派生构造函数都写那个,而是有一个帮助脚本。

如果您对JavaScript继承层次结构感兴趣,您可能需要查看我的简短Lineage脚本 - 不一定要使用,而是要了解这些内容的工作原理。 page showing how to do things without the script与使用脚本进行比较可能特别有用。

答案 1 :(得分:0)

嗨,请仔细阅读以下内容。我希望它能让你对继承和call()

有所了解
<script type="text/javascript">   

    //inheritence
    function parent() {
        this.add = function (a, b) {
            return a + b;
        }
        this.subtract = function (a, b) {
            return a - b;
        }
    }

    function child() {
        this.display = function () {
            alert(this.add(11, 23));
        }
    }

    child.prototype = new parent();         //child extends parent.... inheritence
    child.prototype.constructor = child;    //resetting constructor property

    var obj = new child();
    obj.display();

    /*
    .call() and .apply()
    They allow our objects to borrow methods from other objects and invoke them as their own
    */
    var person = {
        name: 'Kundan',
        display: function(name) {
            alert(this.name + ' welcomes ' + name);
        }
    };

    person.display('Dipa'); //Kundan welcomes Dipa

    var person1 = { name: 'Java Master' };
    person.display.call(person1, 'Sachin'); //Java Master welcomes Sachin
    //here person1 object is passed in the call function
    //if we are using call inside a function and want to pass the same function object then this is passed in call function
    /*
    We can pass more parameters as follows

    person.display.call(person1, 'a', 'b', 'c');

    The method apply() works the same way as call() but with the difference that all parameters you want to pass to the method of the other object are passed as an array.
    */
        person.display.apply(person1, ['a', 'b', 'c']);



</script>