javascript 在 JS 中声明成员函数
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/13700273/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Declaring a member function in JS
提问by Yotam
I've tried two ways to declare a member function in JS:
我尝试了两种在 JS 中声明成员函数的方法:
function init() {
var name = "Mozilla";
function displayName() {
alert(name);
}
}
a = new init();
a.displayName()
And
和
function init() {
var name = "Mozilla";
displayName = function() {
alert(name);
}
}
a = new init();
a.displayName()
The first method told me that displayName()
is undefined
. The way I see it a variable of type Function
with nae displayName
is created, and thus it should work.
Any one care to explain why it didn't work?
第一种方法告诉我displayName()
是undefined
. 我看到的方式是创建Function
了 nae类型的变量displayName
,因此它应该可以工作。有人愿意解释为什么它不起作用吗?
Thanks
谢谢
采纳答案by ThiefMaster
To create something like a member function you need to add it to the protoype of the constructor function:
要创建类似成员函数的东西,您需要将其添加到构造函数的原型中:
function init() {
this.name = 'Mozilla';
}
init.prototype.displayName = function() {
alert(this.name);
}
I also highly recommend you to read something about how the object system in JavaScript works. There's a pretty good article about it on MDN: https://developer.mozilla.org/en-US/docs/JavaScript/Introduction_to_Object-Oriented_JavaScript
我还强烈建议您阅读有关 JavaScript 中对象系统如何工作的内容。MDN 上有一篇关于它的很好的文章:https: //developer.mozilla.org/en-US/docs/JavaScript/Introduction_to_Object-Oriented_JavaScript
回答by T.J. Crowder
It doesn't work because that's now how JavaScript works. Just declaring a function within a constructor function doesn't set it up on the object created by the constructor function, you have to make the link between the object and the function explicitly (directly by assigning it to the object, or more often indirectly via a prototype).
它不起作用,因为这就是 JavaScript 的工作方式。只是在构造函数中声明一个函数并没有在构造函数创建的对象上设置它,您必须显式地建立对象和函数之间的链接(直接通过将其分配给对象,或者更多情况下间接通过原型)。
The typical way you do that is via prototypical inheritance, although you can also just assign functions directly to individual objects (more below — but you talked about "member functions," and the typical way you do things like that in JavaScript is via prototypes).
你这样做的典型方法是通过原型继承,尽管你也可以直接将函数分配给单个对象(更多见下文——但你谈到了“成员函数”,你在 JavaScript 中做这样的事情的典型方法是通过原型) .
There are a couple of ways to set up prototypical inheritance. The classic way, which is compatible with a broad range of JavaScript engines even in legacy browsers, is via the prototype
property on constructor functions, which refers to an object. That object becomes the prototype of instances created via new FunctionName
. You add properties to that object to share them amongst the instances created by that function.
有几种方法可以设置原型继承。经典的方式,即使在旧版浏览器中也与广泛的 JavaScript 引擎兼容,是通过prototype
构造函数上的属性,它引用一个对象。该对象成为通过new FunctionName
. 您向该对象添加属性以在该函数创建的实例之间共享它们。
So, using prototypical inheritance:
因此,使用原型继承:
function Init(name) {
this.name = name;
}
Init.prototype.displayName = function() {
alert(this.name);
};
var i = new Init("Mozilla");
i.displayName();
Notes on the above:
上述注意事项:
In JavaScript, the overwhelming convention is that constructor functions start with an upper case letter. So I called it
Init
rather thaninit
.All functions automatically have a
prototype
property on them, which is a blank object.I add a property to that object called
displayName
which refers to a function.Rather than hard-coding the name, I pass it into
Init
as an argument.Note that I store the name on a property on the newly-constructed instance; within the call to
Init
, that instance is available asthis
.Similarly, because
displayName
is called as part of an expression retrieving the function reference from the object,this
is the object within the call todisplayName
, and sothis.name
has the name.To keep things simple in the above, I assigned an anonymous function to
displayName
. (The property has a name, the function does not.) I tend not to do that in real code.All instances constructed via
new Init
will share the same copy of thedisplayName
function, via the prototype.
在 JavaScript 中,压倒性的约定是构造函数以大写字母开头。所以我叫它
Init
而不是init
.所有的函数都会自动拥有一个
prototype
属性,它是一个空白对象。我向该对象添加了一个属性,该对象
displayName
引用了一个函数。我没有对名称进行硬编码,而是将其
Init
作为参数传入。请注意,我将名称存储在新构建的实例的属性上;在对 的调用中
Init
,该实例可用作this
。类似地,由于
displayName
被称为检索来自物体的函数参照表达式的一部分,this
是调用内的对象displayName
,因此this.name
具有名称。为简单起见,我将匿名函数分配给
displayName
. (属性有名称,函数没有。)我倾向于在实际代码中不这样做。通过原型构造的所有实例
new Init
将共享相同的displayName
函数副本。
More to explore (on my blog):
更多探索(在我的博客上):
You might also be interested in my Lineage
toolkit, if you're interested in building classes of objects in JavaScript (and hierarchies).
如果您对在 JavaScript 中构建对象类(和层次结构)感兴趣,您可能也对我的Lineage
工具包感兴趣。
As of ES5, there's another option: Object.create
. This allows you to create objects and assign them prototypes directly, without using constructor functions. But as you used new
, which means you're using constructor functions, I won't go into detail on that.
从 ES5 开始,还有另一种选择:Object.create
. 这允许您创建对象并直接为其分配原型,而无需使用构造函数。但是正如您所使用的new
,这意味着您正在使用构造函数,我不会详细说明。
Now, you don't haveto use the prototype features of JavaScript if you don't want to. You can, for instance, do this:
现在,你不必有使用JavaScript的原型特征,如果你不想。例如,您可以这样做:
function Init(name) {
var name = name;
this.displayName = function() {
alert(name);
};
}
var i = new Init("Mozilla");
i.displayName();
That doesn't use the prototype features of JavaScript, instead it just creates a new displayName
function every time you call Init
and assigns it directly to the object. (Any reasonable quality JavaScript engine will be smart enough to reuse the codeof the function, but there will be distinct function objectsfor each instance). The above also makes the name
property completely private, because the function we create on each call is a closureover the local variable name
. (More: Closures are not complicated)
它没有使用 JavaScript 的原型特性,而是在displayName
每次调用时创建一个新函数Init
并将其直接分配给对象。(任何质量合理的 JavaScript 引擎都足够智能以重用函数的代码,但每个实例都有不同的函数对象)。上面也使name
属性完全私有,因为我们在每次调用时创建的函数是对局部变量的闭包name
。(更多:闭包并不复杂)
回答by janith
The following should work:
以下应该工作:
function Init() {
var name = "Mozilla";
this.displayName = function() {
alert(name);
}
}
a = new Init();
a.displayName()
回答by Kodemon
One of the standards you can use is
您可以使用的标准之一是
var init = (function() {
var name = "Mozilla"; // Shared by all instances
function init() {
this.name = "IE"; // Spesific to the created instance
}
init.prototype = {
displayName: function() {
alert(name);
alert(this.name);
}
}
return init;
})();
var a = new init();
a.displayName();?
回答by Wang Wei Qiang
In your first method:
在您的第一种方法中:
function init() { var name = "Mozilla"; function displayName() { alert(name); } } a = new init(); a.displayName()
function init() { var name = "Mozilla"; 功能显示名称(){ 警报(名称);} } a = new init(); a.显示名称()
function displayName(){} only can be called in init(), it's like private function, so can not be used as a public function of the object(init())
function displayName(){} 只能在init()中调用,就像私有函数,不能作为对象的公共函数(init())