1. 程式人生 > >JavaScript學習總結(三、函數聲明和表達式、this、閉包和引用、arguments對象、函數間傳遞參數)

JavaScript學習總結(三、函數聲明和表達式、this、閉包和引用、arguments對象、函數間傳遞參數)

rem [1] incr foo i++ scrip erro ren 推薦

一、函數聲明和表達式

函數聲明: function test() {};

test(); //運行正常

function test() {};

函數表達式: var test = function() {};

test; //undefined

test(); //TypeError

var test = function() {};

命名函數的賦值表達式:

var test = function bar() {

test(); //正常運行

};

test(); //ReferenceError

二、this

1. 全局範圍內、函數調用、方法調用、調用構造函數、顯示的設置this;

註:在嚴格模式下,沒有全局變量,即this = undefined,在對象的字面量聲明語法中,this不能用來指向對象本身;

顯示的設置this:

function test(a, b, c) {};

var bar = {};

foo.apply(bar, [1, 2, 3]); //數組將被擴展;

foo.call(bar, 1, 2, 3); //傳遞到test的參數為: a = 1, b = 2,c = 3;

當使用Function.prototype上的call或apply方法時,函數內的this將被顯示設置為函數調用的第一個參數;

2. 常見誤解

1. Foo.method = function() {

  function test() {

    //this 為全局變量;

  };  

  test();

};

Foo.method = function() {

  var that = this;

  function test() {

    //that指向Foo對象;

  };

  test();

};

三、閉包和引用

閉包:當前作用域總是能訪問外部作用域中的變量。

例:

function counter(start) {

  var count = start;

  return {

    increment: function() {

      count++;

    },

    get: function() {

      return count;

    }

  };

};

var test = counter(4);

test.increment();

test.get(); //5;

循環中的閉包:

for (var i = 0; i < 10; i++) {

  setTimeout(function() {

    console.log(i); // 10個10;

  }, 1000);

};

方法:

1. for (var i = 0; i < 10; i++) {

  (function(e) {

    setTimeout(function() {

      console.log(e); // 0, 1, 2, 3, 4, 5, 6, 7, 8, 9

    }, 1000);

  })(i);

};

2. for (var i = 0; i < 10; i++) {

  setTimeout(function(e) {

    return function() {

      console.log(e); //0, 1, 2, 3, 4, 5, 6, 7, 8, 9

    };

  }(i), 1000);

};

四、arguments對象

每個函數內都可以訪問一個變量arguments,它維護著所有傳進來的參數列表,不是一個數組,不能用pop()、push()等數組方法,但是能訪問其length;

註:當arguments作為局部變量聲明和形參時,arguments對象不會被創建;

註:強烈建議不要使用arguments.callee;

轉換為數組:Arrary.prototype.slice.call(arguments);但轉化比較慢,不咋推薦;

arguments會創建getter和setter方法,改變形參的值會改變arguments對象的值,反之亦然;

例:

function test(a, b, c) {

  arguments[0] = 10;

  console.log(a); //10;

  b = 20;

  console.log(arguments[1]); //20;

  var d = c;

  d = 9;

  console.log(c); //3;

};

test(1, 2, 3);

function test(a) {

  ‘use strict‘;

  a = 10;

  console.log(a, arguments[0]); //10, 1

};

test(1);

五、函數間傳遞參數

1. function foo() {

  test.apply(null, argument);

};

function(a, b, c) {};

2. 同時使用call和apply:

function Foo() {};

Foo.prototype.method = function(a, b, c) {

  console.log(this, a, b, c);

};

Foo.method = function() {

  Foo.call.apply(Foo.prototype.method, arguments);

};

或者:

Foo.method = function() {

  var args = Array.prototype.slice.call(arguments);

  Foo.prototype.method.apply(args[0], args.slice[1]);

};

JavaScript學習總結(三、函數聲明和表達式、this、閉包和引用、arguments對象、函數間傳遞參數)