为什么匿名函数中的私有变量可以从 javascript 中的函数外部访问
Why private variables in an anonymous function are accessible from outside the function in javascript?
看了一本《基本JS设计模式》一书后,我无法理解这段代码中私有变量的行为:
var SingletonTester = (function () {
// options: an object containing configuration options for the singleton
// e.g var options = { name: "test", pointX: 5};
function Singleton( options ) {
// set options to the options supplied
// or an empty object if none are provided
options = options || {};
// set some properties for our singleton
this.name = "SingletonTester";
this.pointX = options.pointX || 6;
this.pointY = options.pointY || 10;
}
// our instance holder
var instance;
// an emulation of static variables and methods
var _static = {
name: "SingletonTester",
// Method for getting an instance. It returns
// a singleton instance of a singleton object
getInstance: function( options ) {
if( instance === undefined ) {
instance = new Singleton( options );
}
return instance;
}
};
return _static;
})();
var singletonTest = SingletonTester.getInstance({
pointX: 5
});
// Log the output of pointX just to verify it is correct
// Outputs: 5
console.log( singletonTest.pointX );
这是一本书中关于单例模式的一个例子。
有一个匿名函数,它返回一个包含"name"成员的对象和"getInstance"方法,用于返回"Singleton"函数的实例。
我的问题是了解存储在SingletonTester中的对象如何访问"实例"私有var。我的意思是,在匿名函数完成其工作后,SingletonTester 变量应该只保存对象:
{
name: "SingletonTester",
// Method for getting an instance. It returns
// a singleton instance of a singleton object
getInstance: function( options ) {
if( instance === undefined ) {
instance = new Singleton( options );
}
并且此对象不知道实例是什么。"单例"函数的实例化也是如此。它如何知道在匿名函数范围内定义的"单例"是什么函数?
你正在经历的是JavaScript中的词法范围。基本上,每当您执行一个函数时,您都可以访问该函数的作用域。除此之外,您还可以访问定义函数的词法范围。
我们来看一个例子:
var someObject = (function () {
var privateVariable = 18;
var getValue = function () {
return privateVariable;
};
return {
getValue: getValue
};
})();
对象 'someObject' 有一个方法 'getValue',它在执行时返回值 18。但这怎么可能呢?以下是 JavaScript 引擎在尝试执行 someObject.getValue() 时的工作方式:
- JavaScript引擎对someObject对象执行属性查找,并看到它有自己的getValue属性。
- 找到函数对象 (getValue) 后,它就会执行函数。
- 当函数被执行时,JavaScript引擎会尝试查找privateVariable的值。
- 但是,在"getValue"函数的范围内,privateVariable并不存在。
- 因此,JavaScript 引擎会查看 PARENT 作用域(即声明 getValue 函数的作用域)。
- 此作用域对应于匿名函数的作用域。在此范围内,privateVariable 的值为 18。
这就是 JavaScript 中的词汇范围。关于您的示例,这就是为什么 SingletonTester 的实例可以访问"实例"变量的原因。
我强烈推荐这本书来了解更多信息:范围和闭包
相关文章:
- 从函数JavaScript返回不可变数组/对象
- 将对象传递给函数.JavaScript
- 如何定义const函数javascript(语法糖)
- 新的日期函数javascript
- TypeError:this.getAttribute不是一个函数-javascript
- 从函数javascript发送变量
- 扩展自容器函数Javascript
- 从内部函数javascript内部分配外部函数的对象
- 使用函数JavaScript中的函数
- 在这里使用回调函数(JavaScript)有什么好处吗
- 来自函数 Javascript 的 NaN 返回值 ||函数执行顺序
- 将“e”传递给一个新函数 - javascript
- 调用函数中的一个函数——Javascript
- 传递的变量不适用于我的函数-Javascript
- 如何将类方法设置为等于多个函数?-Javascript
- 显示php中的函数javascript
- 如何使用php代码创建函数Javascript弹出框
- 未调用的外部函数-javascript
- 如何在类中运行函数.Javascript
- 关闭mouseover上的一个函数——Javascript,jQuery