关于nodejs面试题详解

nodejs的一个经典面试题

this.d = 4;
exports.c = 3;
module.exports = {
     a: 1,
     b: 2
 }
//module.exports.a = 1
//module.exports.b = 2

const a = require('./a.js')
console.log(a);

这里执行的结果是:
在这里插入图片描述

。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。。

this.d = 4;
exports.c = 3;
//module.exports = {
//     a: 1,
//     b: 2
// }
module.exports.a = 1
module.exports.b = 2
const a = require('./a.js')
console.log(a);

这里执行的结果是:
在这里插入图片描述
这里仅仅只是两个的输出方式不一样就导致了不一样的结果,其原因是有关node的底层代码:
因为require执行的时候会经过以下几个步骤:
注意以下代码都是理论代码不能执行,只是用作分析
1.调用了resolve方法拼接成了一个绝对路径


function require(modulePath){//模块路径
	
}

2.在cache部分判断该模块是否有缓存。cache是require函数的缓存区

	if(require.cache["C:\\Users\\admin\\Desktop\\0315nodejs\\04.js"]){
		return require.cache["C:\\Users\\admin\\Desktop\\0315nodejs\\04.js"]
	}	

3.读取目标文件内容
4.包裹到一个函数中去


function require(modulePath){//模块路径
	if(require.cache["C:\\Users\\admin\\Desktop\\0315nodejs\\04.js"]){
		return require.cache["C:\\Users\\admin\\Desktop\\0315nodejs\\04.js"]
	}	
	function _temp(module,exports,require,__dirname,__filename){
	//在require目标对象的所有代码都在这个内部函数执行
		this.d = 4;
		exports.c = 3;
		module.exports = {
			a : 1,
			b : 2
		}
	}
}
	

5.创建module.exports对象(重点)

function require(modulePath){//模块路径
	if(require.cache["C:\\Users\\admin\\Desktop\\0315nodejs\\04.js"]){
		return require.cache["C:\\Users\\admin\\Desktop\\0315nodejs\\04.js"]
	}	
	function _temp(module,exports,require,__dirname,__filename){
	//在require目标对象的所有代码都在这个内部函数执行
		this.d = 4;
		exports.c = 3;
		module.exports = {
			a : 1,
			b : 2
		}
	}
	// 5.创建module.exports对象
		module.exports = {}
		const exports = module.exports
		_temp.call(module.exports,exports,require,__dirname,__filename)
	
		return module.exports;
}

在执行内部函数_temp的时候它会通过call来改变this的指向将其指向module.exports同时创建module.exports对象,然后创建exports同时把module.exports赋值exports也就是说现在this、module.exports、exports其实是一个东西:

console.log(module.exports === exports)//true
console.log(module.exports === this)//true

最后返回module.exports;

所以说

this.d = 4;
exports.c = 3;
module.exports.a = 1
module.exports.b = 2

输出{d:4, c:3, a:1, b:2}是因为它们都在往module.exports里加东西;

但是

this.d = 4;
exports.c = 3;
module.exports = {
     a: 1,
     b: 2
 }

这里就有问题了一开始本来就创建了个module.exports的空对象,现在有赋值了一个新的对象。这就导致了module.exports指向了一个新的地址
这里我画个图来表示
第一种情况:
在这里插入图片描述
第二种情况:
在这里插入图片描述
而require函数返回的是module.exports自然也就输出的是{a:1,b:2}了

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值