提问人:Gökçer Gökdal 提问时间:4/1/2014 最后编辑:Gökçer Gökdal 更新时间:9/7/2018 访问量:50304
node.js 模块和函数中“this”的含义
Meaning of "this" in node.js modules and functions
问:
我有一个由 .require
// loaded by require()
var a = this; // "this" is an empty object
this.anObject = {name:"An object"};
var aFunction = function() {
var innerThis = this; // "this" is node global object
};
aFunction();
(function(anyParameter){
console.log(anyParameter.anObject);
})(
this // "this" is same having anObject. Not "global"
);
我的问题是:var 中是一个空对象,而函数中的语句是 node.js 全局对象的影子。我知道关键字在函数中是不同的,但我不明白为什么 first 不等于 global,而 in functions 等于 global。this
a = this;
this
this
this
this
node.js 如何在函数作用域中注入,为什么它不将其注入到模块作用域?global
this
答:
以下是您必须了解的一些基本事实,以澄清情况:
在 Node 模块的顶级代码中,等效于 。这就是你看到的空物体。
this
module.exports
当您在函数内部使用时,在每次执行函数之前都会重新确定 的值,其值由函数的执行方式决定。这意味着,如果调用机制不同(例如 与。 vs. 等)在您的情况下,在非严格模式下运行设置为全局对象的函数。
this
this
this
aFunction()
aFunction.call(newThis)
emitter.addEventListener("someEvent", aFunction);
aFunction()
this
当 JavaScript 文件作为 Node 模块时,Node 引擎会在包装函数内运行模块代码。调用该模块包装函数时,设置为 。(回想一下,上面,一个函数可以用一个 abitrary 值运行。
require
this
module.exports
this
因此,您将获得不同的值,因为每个值都位于不同的函数中:第一个值位于 Node 创建的模块包装函数中,第二个值位于 中。this
this
aFunction
评论
apply
return compiledWrapper.apply(self.exports, args);
要理解这一点,您需要了解 Node.js 实际上将您的模块代码包装到一个函数中,如下所示
(function (exports, require, module, __filename, __dirname) {
var test = function(){
console.log('From test: ' + this);
};
console.log(this);
test();
});
详细的解释可以在这个答案中找到。
现在,这个包装的函数实际上是这样调用的
var args = [self.exports, require, self, filename, dirname];
return compiledWrapper.apply(self.exports, args);
因此,在
模块级别,这实际上是导出
对象。
您可以像这样确认
console.log(this, this === module.exports);
// {} true
评论
test
this
fn()
this
use strict
this
this
exports
这是因为 Node.js 模块中的默认全局对象是该对象,并且您正在调用未指定 .在传统的 JS 中,指向全局对象,其中 将为 null。exports
test()
this
this
use strict
this
this
可以指向任何东西,这取决于你如何称呼它。
test()
:使用全局对象 () 作为 ,除非在严格模式下,where 将为 null;exports
this
this
test.call({})
或 :您指定要用作的内容(第一个参数)test.apply({})
this
var obj = {testRef: test}; obj.testRef()
:设置在 的左侧,即this
.
obj
反驳第四只眼的回答
的确,在模块的顶层是 ,但这并不一定意味着 inside 也会指向与调用它的位置相同的事物。this
exports
this
test()
试图证明 this
和 global 对象都指向 exports
myGLobal = 5;
this.myGlobal; // 5
评论
global object in Node.js is the exports object
- 这是不正确的。每个模块都有自己的对象。exports
global
global.myName = 'Mike';
global.myName
myName
var myName = 'Mike';
myName = 'Mike'
总结:
在 Javascript 中,值是在调用函数时确定的。创建函数时不行。在 nodeJS 中,在模块的最外层作用域中,其值是当前对象。当函数作为对象的属性调用时,此值将更改为被调用的对象。你可以简单地记住这一点,只需点左边的规则:this
this
module.exports
调用函数时,可以通过查看函数调用的位置来确定函数的值。点左边的对象是 的值。如果点上没有对象,则 的值是对象(在浏览器中)。
this
this
this
module.exports
window
警告:
- 此规则不适用于没有自己的绑定的箭头函数。
es2015
this
- 函数 、 和 可以弯曲有关值的规则。
call
apply
bind
this
示例 (NodeJS):
console.log(this); // {} , this === module.exports which is an empty object for now
module.exports.foo = 5;
console.log(this); // { foo:5 }
let obj = {
func1: function () { console.log(this); },
func2: () => { console.log(this); }
}
obj.func1(); // obj is left of the dot, so this is obj
obj.func2(); // arrow function don't have their own this
// binding, so this is module.exports, which is{ foo:5 }
输出:
评论
module.exports = {a:4}console.log(this)
评论
一些文档
。请注意,文档通常假设 JS 在浏览器中运行,因此“全局对象”将代替 NodeJS 全局对象,但概念是相同的。一些更相关的文档是 NodeJS的 this
docs。this
window
this
global
this
global
this
aFunction