可能是我在这里遗漏了一些东西。请耐心等待,因为我是javascript中的OOP新手。但我需要找到解决问题的方法。
我有这段代码。
var parent = function() {}
parent.prototype.someFunc = function() {
return "a string";
}
现在我正在尝试使用下面的代码继承父级,
var child = function() {
parent.call(this);
}
child.prototype = new parent();
当我这样做时,它有效。
var obj = new child();
obj.someFunc();
但是我希望在下面的子项中有someFunc(),
var child = function() {
parent.call(this);
var someVal = this.someFunc(); // method from parent.
}
child.prototype = new parent();
这样做会给我一个错误Uncaught TypeError: Object [object global] has no method 'getLightBox'
但是据我所知this
指的是当前对象,我只是在这里混淆了如何解决这个问题。如果我错了,请纠正我。或者,如果有更好的方法,那么我想了解它。
答案 0 :(得分:3)
您忘记使用new
。 I.E.你有代码child(...)
代替new child(...)
一些提示:
new
会导致即时错误Parent
而非parent
所以忘记new
会像拇指一样伸出来。事实上JSHint can statically find where you forgot to use new
if you follow this practice。new
会再次像拇指一样伸出来。另外
new
链接原型,只需执行Child.prototype = Object.create(Parent.prototype)
答案 1 :(得分:2)
首选解决方案
Javascript OOP在上下文处理中是特定的:如果您的父级使用上下文( this ),只需使用其上下文调用子级中的父级(请注意 new function(),用于设置从全局到新创建的对象的上下文:
var parent = function() { // constructor, should be called with new
this.someFunc = function() { return "a string"; }
}
var child = new function() { // object, was already called with new
parent.call(this); // set parent context to child's, don't create new one
var someVal = this.someFunc(); // method from parent.
}
console.log(child.someFunc()); // a string
替代的非标准解决方案,接近您的方法
如果您设置父原型而不是使用其上下文,则可以使用非标准 __proto__
成员,该成员可以访问其原型:
var parent = function() {} // constructor to create empty object
parent.prototype.someFunc = function() { // someFunc is in parent prototype
return "a string";
}
var child = new function() {
this.__proto__ = new parent(); // set prototype to parent with its own context
var someVal = this.someFunc(); // method from parent.
}
console.log(child.someFunc()); // a string
与您的工作示例相比
您也可以使用标准 prototype
将原型设置为构造函数,而不是对象。请注意,在设置原型后创建对象,查看new
调用的位置,并将其与Felix Kling对问题的评论进行比较:
var parent = function() {}
parent.prototype.someFunc = function() {
return "a string";
}
var child = function() { // no new here
var someVal = this.someFunc();
}
child.prototype = new parent();
console.log((new child).someFunc()); // new moved here
错误解释
new
的函数在javascript中从函数创建构造函数。这意味着上下文成为函数本身。没有new
(并且具有默认的非严格行为),上下文是全局上下文,因此您的错误
Object [object global] has no method 'someFunc'
答案 2 :(得分:2)
嘿哥们,你的概念错了。 首先,您需要了解您在代码中所做的以下问题
你在这里使用了组合形式的继承 原型链接(实现继承)以孩子的原型是父实例的方式// somefunc()实际上是以这种方式继承到子的原型而不是子的实例//
构造函数Stealing(Classical Inheritence)通过在Child Constructor中调用Parent构造函数//没有以这种方式继承//
所以这里的问题是你遇到了几乎每个初学者都使用Combined Inheritence的问题。 问题是
在组合的Inheritence中,我们两次调用SuperType(parent)。一次通过经典的继承和其他使child.prototype成为父实例 你从经典继承(即从子构造函数中)开始第一次调用。这次你没有创建child.prototype作为实例 父对象和你正在使用this.someFunc()通过原型继承分配给子实例。这是错误的原因。
解决方案:首次调用父对象,将子原型设置为父对象的实例[child.prototype = new parent();] ans然后进行第二次调用 [创建孩子的实例] ..
简而言之,我的意思是
<script>
var parent = function() {}
parent.prototype.someFunc = function() {
return "a string";
}
var child = function() {
parent.call(this);
someVal = this.someFunc(); // method from parent.
}
child.prototype = new parent();
var obj = new child();
alert(someVal);
</script>
更好的解决方案是使用Parasitic Combination Inheritence,其中父对象只被调用一次 通过经典的继承。
答案 3 :(得分:1)
确保你试图调用的函数是在父对象的原型上,而不是在它自己的对象上(类方法vs“静态”方法)如果方法是“静态的”你不能在它中调用它有这个但有
的儿童班parent.method.call(this)
答案 4 :(得分:1)
我不确定你期望的是什么,但如果你想将someVal作为Child的一个属性并在创建实例后被访问,那么你应该使用this.someVal而不是var someVal声明它。
在函数体中声明的用于创建具有var的对象实例的变量是一个坏主意,因为这些变量仅在函数体中可用而不在原型函数中。
可以在此处找到有关JS原型如何工作的基本说明:Prototypical inheritance - writing up
您提供的代码应该没有问题:
var parent = function() {}
parent.prototype.someFunc = function() {
return "a string";
}
var child = function() {
parent.call(this);
var someVal = this.someFunc(); // method from parent.
console.log("someval in child body",someVal);
this.publicProp=this.someFunc();
}
child.prototype = new parent();
var c = new child();
console.log("return value of someFunc",c.publicProp);