function a() {
var num = 100;
function b() {
num ++;
console.log(num);
}
return b;
}
var demo = a();
demo(); // 101 aAO{ num: 101} 保存到了demo 执行完b被销毁
demo(); // 102 aAO{ num: 102} num读的是aAO里的
当内部函数被保存到外部时,将会生成闭包。闭包会导致原有作用域链不释放,造成内存泄露。
闭包的作用
- 实现公有变量
//函数累加器
function add() {
var count = 0;
function demo(){
count ++;
console.log(count);
}
return count;
}
var counter = add();
counter(); // 1
counter(); // 2
counter(); // 3
- 可以做缓存(存储结构)
// 公用一个testAO
function test() {
var num = 100;
function a() {
num ++;
console.log(num);
}
function b() {
num --;
console.log(num);
}
return [a,b];
}
var myArr = test();
myArr[0](); // 101
myArr[1](); // 100
-
可以实现封装,属性私有化// function eater() { var food = ''; var obj = { eat:function () { console.log('i am eating ' + food); food = ''; }, push: function (myFood) { food = myFood; } } return obj; } var eater1 = eater(); eater1.push('banana'); eater1.eat();
Person()
- 模块化开发,防止污染全局变量.
var name = 'xiaowang';
var initZhang = (function(){
var name = 'xiaozhang';
function sayName() {
console.log(name);
}
return function(){
sayName();
}
}())
var initLiu = (function(){
var name = 'xiaoliu';
function sayName() {
console.log(name);
}
return function(){
sayName();
}
}())
initZhang(); // 'xiaozhang'
initLiu(); // 'xiaoliu';
立即执行函数
针对初始化功能的函数
执行完就会立即释放
// 书写规范
// (function (){}()); // w3c建议
// (function (){})();
// 执行完 立即销毁 执行完就被释放
(function(){
var a = 123;
var b = 234;
console.log(a + b);
}())
// 返回值
var num = (function (a,b,c){
var d = a + b + c * 2 + 2 - 5;
return d;
}(1,2,3))
// 只有表达式才能被执行符号执行
// 函数声明
// function test(){}
// function test(){}() // 报错 函数声明不能直接执行
// 正确打开方式 test()
// 函数表达式
var test = function(){
console.log(1);
}() // 加() 立即执行
// 能被执行符号执行的表达式 名字自动被忽略
var test2 = function (){
console.log(2);
}()
test2(); // undefined; 因为立即执行过了,所以不能使用
// + - ! 正 负 非 先要把后面转换为Number 后面有执行括号 所以先执行后转换 如果不加执行符号 函数不会执行 log 不会输出 但res结果还是为 NaN
var res = + function test(){
console.log(3); // 不会报错 正常输出
}()
- function test(){
console.log(4); // 不会报错 正常输出
}()
! function test(){
console.log(5); // 不会报错 正常输出
}()
// && || / * 前面需要有个值 a结果为NaN
var a = 1 * function(){
console.log('11');
}()
// 不会报错 不会输出
function demo(a,b,c,d) {
console.log(a + b + c + d);
}(1,2,3,4)
// 运行时 为了不报错 系统当做逗号操作符
// 解析为
//function demo(a,b,c,d) {
// console.log(a + b + c + d);
//}
//(1,2,3,4)
// demo // 输出 function demo(a,b,c,d) { console.log(a + b + c + d)};