gpt4 book ai didi

javascript - 用原型(prototype)替换 __proto__

转载 作者:行者123 更新时间:2023-11-30 07:40:59 24 4
gpt4 key购买 nike

我倾向于用 C 风格编写我的 Javascript“类”。

在 C# 中(例如)我们这样做

public class Parent {
// stuff
}

public class Child : Parent {
// Protected and public stuff from Parent will be accessible
}

在 JS 中,我通过使用 proto 找到了等效的例子

var namespace = namespace || {};

namespace.Parent = function() {

// Public variables
self.pubVariable = "I am accessible";

// Private variables
var priVariable = "I'm not accessible outside of self";

// ctor
function self() {}

return self;
}


namespace.Child = (function() {
this.__proto__ = new namespace.Parent();

// ctor
function self() {}

self.init = function() {
// Prints the pubVariable
console.log(pubVariable);
};

return self;

})($);

// Call it (statically)
namespace.Child.init();

虽然这只适用于 Webkit 和 Mozilla。我知道这可以通过原型(prototype)以某种方式实现,但不知道如何实现。任何建议表示赞赏。谢谢!

最佳答案

对于父/子类,我会做这样的事情

// your parent class
var Parent = function() {

// parent constructor
console.log("parent constructor!");

// some public properties
this.foo = "foo";
this.bar = "bar";

// a private data member
var secret = "123456";
};

// a parent function
Parent.prototype.something = function() {
console.log("something!");
}

// your child class
var Child = function() {

// call parent constructor
Parent.call(this);

// child constructor
console.log("child constructor!");

// override bar
this.bar = "override!";
};

// the magic!
// child prototype build from parent prototype
Child.prototype = Object.create(Parent.prototype, {constructor: {value: Child}});

示例用法

var c = new Child();
c.something();
// => parent constructor!
// => child constructor!
// => something!

c.foo //=> "foo"
c.bar //=> "override!"

如果您使用的是“命名空间”,则概念是相同的。


编辑

根据您的评论,这里是并添加了演示

var Foo = function(){};
Foo.prototype.hello = function(){ return "hello!"; };
var foo = new Foo();

// call our hello method
// this calls foo.__proto__.hello
foo.hello(); //=> "hello!"

// override `hello` method for this instance
foo.hello = function(){ return "こんにちは"; };

// call our hello method again
// this calls foo.hello because it is defined directly on our instance
// (it has a higher precedence in the lookup chain)
foo.hello(); //=> "こんにちは"

// remove the override
delete foo.hello;

// call our hello method again
// this goes back to calling foo.__proto__.hello
foo.hello(); //=> "hello!"

// remove the method prototype
delete Foo.prototype.hello

// call our hello method one last time
// spoiler: it's gone!
foo.hello(); //=> TypeError: Object [object Object] has no method 'hello'

如您所见,使用 this.something = function(){}; 直接在实例上定义方法会失去此功能。我个人更喜欢在原型(prototype)上定义方法,因为它增加了灵 active 。这样,原型(prototype)就真的像蓝图一样工作了。您将获得所有预定义的行为;您可以根据需要进行修改,并随时恢复为原始状态,所有这些都基于每个实例。


还有一件事

在我们的最后一个例子中,我们有一个原型(prototype)方法和一个实例方法覆盖。有没有办法也调用原始方法?让我们看看!

var Foo = function(){};
Foo.prototype.hello = function(){ return "hello!"; };

var foo = new Foo();
foo.hello = function(){ return "こんにちは!"; }

// call override method
foo.hello(); //=> "こんにちは!"

// call original method
Foo.prototype.hello.call(foo); //=> "hello!"

// japanese just one more time...
foo.hello(); //=> "こんにちは!"

这也行,但我从来没有真正需要。我想这样做的好处是您不需要通过这种方式了解原始类(class) :)

// call original method from the instance
foo.__proto__.hello.call(foo); //=> "hello!"

原型(prototype)!

关于javascript - 用原型(prototype)替换 __proto__,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/17263299/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com