欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

JS中call/apply、arguments、undefined/null方法詳解

 更新時(shí)間:2016年02月15日 17:20:40   作者:chua1989  
這篇文章主要介紹了JS中call/apply、arguments、undefined/null方法詳解的相關(guān)資料,需要的朋友可以參考下

a.call和apply方法詳解
--------------------------------------------------------------------------------

call方法:

  語法:call([thisObj[,arg1[, arg2[, [,.argN]]]]])

  定義:調(diào)用一個(gè)對(duì)象的一個(gè)方法,以另一個(gè)對(duì)象替換當(dāng)前對(duì)象。

  說明: call 方法可以用來代替另一個(gè)對(duì)象調(diào)用一個(gè)方法。call 方法可將一個(gè)函數(shù)的對(duì)象上下文從初始的上下文改變?yōu)橛?thisObj 指定的新對(duì)象。如果沒有提供 thisObj 參數(shù),那么 Global 對(duì)象被用作 thisObj。

apply方法:

  語法:apply([thisObj[,argArray]])

  定義:應(yīng)用某一對(duì)象的一個(gè)方法,用另一個(gè)對(duì)象替換當(dāng)前對(duì)象。

  說明:如果 argArray 不是一個(gè)有效的數(shù)組或者不是 arguments 對(duì)象,那么將導(dǎo)致一個(gè) TypeError。如果沒有提供 argArray 和 thisObj 任何一個(gè)參數(shù),那么 Global 對(duì)象將被用作 thisObj, 并且無法被傳遞任何參數(shù)。

實(shí)例學(xué)習(xí):

function add(a,b){ alert(a+b);}
function sub(a,b){ alert(a-b);}
add.call(sub,3,1); 

  打印結(jié)果為4。調(diào)用add函數(shù),但是調(diào)用對(duì)象(上下文環(huán)境)不是add對(duì)象,而是sub函數(shù)對(duì)象。注意:js中的函數(shù)其實(shí)是對(duì)象,函數(shù)名是對(duì) Function 對(duì)象的引用。

function Animal(){ 
this.name = "Animal"; 
this.showName = function(){ alert(this.name);} 
}
function Cat(){ this.name = "Cat"; } 
var animal = new Animal(); 
var cat = new Cat(); 
animal.showName.call(cat,",");//輸出結(jié)果為"Cat"
animal.showName.apply(cat,[]);//輸出結(jié)果為"Cat" 

  call 的意思是把 animal 的方法放到cat上執(zhí)行,上下文環(huán)境為cat,原來cat是沒有showName() 方法,現(xiàn)在是把a(bǔ)nimal 的showName()方法放到 cat上來執(zhí)行,而cat的this.name是Cat。所以this.name 應(yīng)該是 Cat

實(shí)現(xiàn)繼承

function Animal(name){ 
this.name = name; 
this.showName = function(){ alert(this.name);} 
} 
function Cat(name){ Animal.call(this, name); } 
var cat = new Cat("Black Cat"); 
cat.showName(); 

  Animal.call(this) 的意思就是調(diào)用Animal方法,但是使用 this對(duì)象代替Animal對(duì)象,上下文環(huán)境變成了this。new Cat("Black Cat")中使用Animal.call給當(dāng)前的上下文環(huán)境設(shè)置了屬性name和方法showName。

拓展:多重繼承

function Class10(){
this.showSub = function(a,b){ alert(a-b); }
}
function Class11(){
this.showAdd = function(a,b){ alert(a+b); }
}
function Class2(){
Class10.call(this);
Class11.call(this);
}

  備注:js的繼承還有其他方法,例如使用原型鏈,這個(gè)不屬于本文的范疇,只是在此說明call 的用法。說了call ,當(dāng)然還有 apply,這兩個(gè)方法基本上是一個(gè)意思,區(qū)別在于 call 的第二個(gè)參數(shù)可以是任意類型,而apply的第二個(gè)參數(shù)必須是數(shù)組或arguments。

b.arguments使用

--------------------------------------------------------------------------------

什么是arguments

  arguments 是是JavaScript里的一個(gè)內(nèi)置對(duì)象,它很古怪,也經(jīng)常被人所忽視,但實(shí)際上是很重要的。所有主要的js函數(shù)庫都利用了arguments對(duì)象。所以agruments對(duì)象對(duì)于javascript程序員來說是必需熟悉的。

  所有的函數(shù)都有屬于自己的一個(gè)arguments對(duì)象,它包括了函所要調(diào)用的參數(shù)。他不是一個(gè)數(shù)組,如果用typeof arguments,返回的是'object'。雖然我們可以用調(diào)用數(shù)據(jù)的方法來調(diào)用arguments。比如length,還有index方法。但是數(shù) 組的push和pop對(duì)象是不適用的。

使用arguments創(chuàng)建一個(gè)靈活的函數(shù)

  看起來貌似argument對(duì)象使用起來十分有限,但是實(shí)際上它是一個(gè)非常有用的對(duì)象。你可以通過使用argument對(duì)象讓函數(shù)能夠調(diào)用數(shù)量不定 的參數(shù)。在Dean Edwards的base2庫里有個(gè)格式化的函數(shù),展示了這個(gè)靈活性。

function format(string) {
var args = arguments;
var pattern = new RegExp('%([1-' + arguments.length + '])', 'g');
return String(string).replace(pattern, function(match, index,position,all) { 
console.log(match + '&' + index + '&' + position + '&' + all);
return args[index]; 
}); 
}; 

  掉用format('And the %1 want to know whose %2 you %3', 'papers', 'shirt', 'wear');結(jié)果為"And the papers want to know whose shirt you wear";控制臺(tái)打印為

  %1&1&8&And the %1 want to know whose %2 you %3
  %2&2&30&And the %1 want to know whose %2 you %3
  %3&3&37&And the %1 want to know whose %2 you %3

把a(bǔ)rguments對(duì)象轉(zhuǎn)換成一個(gè)真正的數(shù)組

  雖然arguments對(duì)象不是一個(gè)真正的javascript數(shù)組,但是我們還是可以輕易的把它轉(zhuǎn)換成標(biāo)準(zhǔn)的數(shù)據(jù) ,然后進(jìn)行數(shù)組操作。

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

  那么現(xiàn)在這個(gè)變量args就含有一個(gè)含有函數(shù)所有參數(shù)的標(biāo)準(zhǔn)javascript數(shù)組對(duì)象。

拓展:使用上一節(jié)的format函數(shù),通過預(yù)置的arguments對(duì)象創(chuàng)建函數(shù)

function makeFunc() { 
var args = Array.prototype.slice.call(arguments); 
var func = args.shift(); 
return function() { 
return func.apply(null, args.concat(Array.prototype.slice.call(arguments))); 
}; 
} 

  該方法會(huì)將第一個(gè)參數(shù)取出來,然后返回一個(gè)curry化函數(shù),該curry化函數(shù)的參數(shù)(第二個(gè)arguments)將和makeFunc的從第二個(gè)參數(shù)開始的參數(shù)組合成新數(shù)組。并返回makeFunc第一個(gè)參數(shù)的apply調(diào)用

  執(zhí)行

var majorTom = makeFunc(format, "This is Major Tom to ground control. I'm %1.");
majorTom("stepping through the door"); 

  結(jié)果為:"This is Major Tom to ground control. I'm stepping through the door."

  控制臺(tái)打印:%1&1&41&This is Major Tom to ground control. I'm %1.

[function.]arguments.callee

  說明:arguments.callee方法返回的是正在執(zhí)行的函數(shù)本身。

  callee 屬性是 arguments 對(duì)象的一個(gè)成員,它表示對(duì)函數(shù)對(duì)象本身的引用,這有利于匿名函數(shù)的遞歸或者保證函數(shù)的封裝性,例如下邊示例的遞歸計(jì)算1到n的自然數(shù)之和。而該屬性僅當(dāng)相關(guān)函數(shù)正在執(zhí)行時(shí)才可用。還有需要注意的是callee擁有l(wèi)ength屬性,這個(gè)屬性有時(shí)候用于驗(yàn)證還是比較好的。arguments.length是實(shí)參長(zhǎng)度,arguments.callee.length是形參(定義時(shí)規(guī)定的需要的參數(shù))長(zhǎng)度,由此可以判斷調(diào)用時(shí)形參長(zhǎng)度是否和實(shí)參長(zhǎng)度一致。

//用于驗(yàn)證參數(shù)
function calleeLengthDemo(arg1, arg2) {
if (arguments.length==arguments.callee.length) {
window.alert("驗(yàn)證形參和實(shí)參長(zhǎng)度正確!");
return;
} else {
alert("實(shí)參長(zhǎng)度:" +arguments.length);
alert("形參長(zhǎng)度: " +arguments.callee.length);
}
}
//遞歸計(jì)算
var sum = function(n){
if (n <= 0) return 1;
else return n +arguments.callee(n - 1)
}
//比較一般的遞歸函數(shù):
var sum = function(n){
if (1==n) return 1;
else return n + sum (n-1);
}

  調(diào)用時(shí):alert(sum(100));其中函數(shù)內(nèi)部包含了對(duì)sum自身的引用,函數(shù)名僅僅是一個(gè)變量名,在函數(shù)內(nèi)部調(diào)用sum即相當(dāng)于調(diào)用一個(gè)全局變量,不能很好的體現(xiàn)出是調(diào)用自身,這時(shí)使用callee會(huì)是一個(gè)比較好的方法。

拓展 functionName.caller

  說明: 返回是誰調(diào)用了functionName 函數(shù)。functionName 對(duì)象是所執(zhí)行函數(shù)的名稱。對(duì)于函數(shù)來說,caller 屬性只有在函數(shù)執(zhí)行時(shí)才有定義。如果函數(shù)是由頂層調(diào)用的,那么 caller 包含的就是 null 。如果在字符串上下文中使用 caller 屬性,那么結(jié)果和 functionName.toString 一樣,也就是說,顯示的是函數(shù)的反編譯文本。 下面的例子說明了 caller 屬性的用法:

// caller demo {
function callerDemo() {
if (callerDemo.caller) {
var a= callerDemo.caller.toString();
alert(a);
} else {
alert("this is a top function");
}
}
function handleCaller() {
callerDemo();
}
handleCaller(); 

  執(zhí)行結(jié)果:

c.undefined和null

--------------------------------------------------------------------------------

  大多數(shù)計(jì)算機(jī)語言,有且僅有一個(gè)表示"無"的值,比如,C語言的NULL,Java語言的null,Python語言的none,Ruby語言的nil。有點(diǎn)奇怪的是,JavaScript語言居然有兩個(gè)表示"無"的值:undefined和null。這是為什么?

相似性

  在JavaScript中,將一個(gè)變量賦值為undefined或null,老實(shí)說,幾乎沒區(qū)別。

  代碼如下:

var a = undefined;
var a = null; 

  上面代碼中,a變量分別被賦值為undefined和null,這兩種寫法幾乎等價(jià)。

  undefined和null在if語句中,都會(huì)被自動(dòng)轉(zhuǎn)為false,相等運(yùn)算符甚至直接報(bào)告兩者相等。

if (!undefined) 
console.log('undefined is false');
// undefined is false
if (!null) 
console.log('null is false');
// null is false
undefined == null
// true 

  上面代碼說明,兩者的行為是何等相似!但是我們?nèi)ゲ榭磚ndefined和null的各自的類型卻發(fā)現(xiàn)類型是不同的。js基礎(chǔ)類型中沒有null類型

typeof null;//"object"
typeof undefined;//"undefined" 

  既然undefined和null的含義與用法都差不多,為什么要同時(shí)設(shè)置兩個(gè)這樣的值,這不是無端增加JavaScript的復(fù)雜度,令初學(xué)者困擾嗎?Google公司開發(fā)的JavaScript語言的替代品Dart語言,就明確規(guī)定只有null,沒有undefined!

歷史原因

  原來,這與JavaScript的歷史有關(guān)。1995年JavaScript誕生時(shí),最初像Java一樣,只設(shè)置了null作為表示"無"的值。

  根據(jù)C語言的傳統(tǒng),null被設(shè)計(jì)成可以自動(dòng)轉(zhuǎn)為0。

Number(null) // 0
5 + null // 5

  但是,JavaScript的設(shè)計(jì)者Brendan Eich,覺得這樣做還不夠,有兩個(gè)原因。

  首先,null像在Java里一樣,被當(dāng)成一個(gè)對(duì)象。

typeof null // "object"

  但是,JavaScript的數(shù)據(jù)類型分成原始類型(primitive)和合成類型(complex)兩大類,Brendan Eich覺得表示"無"的值最好不是對(duì)象。

  其次,JavaScript的最初版本沒有包括錯(cuò)誤處理機(jī)制,發(fā)生數(shù)據(jù)類型不匹配時(shí),往往是自動(dòng)轉(zhuǎn)換類型或者默默地失敗。Brendan Eich覺得,如果null自動(dòng)轉(zhuǎn)為0,很不容易發(fā)現(xiàn)錯(cuò)誤。因此,Brendan Eich又設(shè)計(jì)了一個(gè)undefined。

最初設(shè)計(jì)

  JavaScript的最初版本是這樣區(qū)分的:null是一個(gè)表示"無"的對(duì)象,轉(zhuǎn)為數(shù)值時(shí)為0;undefined是一個(gè)表示"無"的原始值,轉(zhuǎn)為數(shù)值時(shí)為NaN。

Number(undefined) // NaN
5 + undefined // NaN

目前的用法

  但是,上面這樣的區(qū)分,在實(shí)踐中很快就被證明不可行。目前,null和undefined基本是同義的,只有一些細(xì)微的差別。

  null表示"沒有對(duì)象",即該處不應(yīng)該有值。典型用法是:

  (1) 作為函數(shù)的參數(shù),表示該函數(shù)的參數(shù)不是對(duì)象。

 ?。?) 作為對(duì)象原型鏈的終點(diǎn)。

Object.getPrototypeOf(Object.prototype) // null

  undefined表示"缺少值",就是此處應(yīng)該有一個(gè)值,但是還沒有定義。典型用法是:

  (1)變量被聲明了,但沒有賦值時(shí),就等于undefined。

 ?。?) 調(diào)用函數(shù)時(shí),應(yīng)該提供的參數(shù)沒有提供,該參數(shù)等于undefined。

 ?。?)對(duì)象沒有賦值的屬性,該屬性的值為undefined。

  (4)函數(shù)沒有返回值時(shí),默認(rèn)返回undefined。

var i;
i // undefined
function f(x){console.log(x)}
f() // undefined
var o = new Object();
o.p // undefined
var x = f();
x // undefined 

以上所述是小編給大家介紹的JS中call/apply、arguments、undefined/null方法詳解,希望對(duì)大家有所幫助。

相關(guān)文章

  • JS仿Base.js實(shí)現(xiàn)的繼承示例

    JS仿Base.js實(shí)現(xiàn)的繼承示例

    這篇文章主要介紹了JS仿Base.js實(shí)現(xiàn)的繼承,結(jié)合具體實(shí)例形式分析了javascript擴(kuò)展操作及面向?qū)ο蟪绦蛟O(shè)計(jì)相關(guān)實(shí)現(xiàn)技巧,需要的朋友可以參考下
    2017-04-04
  • HTML5+Canvas調(diào)用手機(jī)拍照功能實(shí)現(xiàn)圖片上傳(上)

    HTML5+Canvas調(diào)用手機(jī)拍照功能實(shí)現(xiàn)圖片上傳(上)

    這篇文章主要為大家詳細(xì)介紹了HTML5+Canvas,和jquery技術(shù),調(diào)用手機(jī)拍照功能實(shí)現(xiàn)圖片上傳,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2017-04-04
  • 深入理解JavaScript系列(34):設(shè)計(jì)模式之命令模式詳解

    深入理解JavaScript系列(34):設(shè)計(jì)模式之命令模式詳解

    這篇文章主要介紹了深入理解JavaScript系列(34):設(shè)計(jì)模式之命令模式詳解,命令模式(Command)的定義是:用于將一個(gè)請(qǐng)求封裝成一個(gè)對(duì)象,從而使你可用不同的請(qǐng)求對(duì)客戶進(jìn)行參數(shù)化,對(duì)請(qǐng)求排隊(duì)或者記錄請(qǐng)求日志,以及執(zhí)行可撤銷的操作,需要的朋友可以參考下
    2015-03-03
  • js函數(shù)般調(diào)用正則

    js函數(shù)般調(diào)用正則

    Firefox 包含了一個(gè)非標(biāo)準(zhǔn)的 JavaScript 擴(kuò)展,使正則像函數(shù)一樣可調(diào)用。
    2008-04-04
  • js實(shí)現(xiàn)水平滾動(dòng)菜單導(dǎo)航

    js實(shí)現(xiàn)水平滾動(dòng)菜單導(dǎo)航

    這篇文章主要為大家詳細(xì)介紹了js實(shí)現(xiàn)水平滾動(dòng)菜單導(dǎo)航,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2017-07-07
  • 12個(gè)非常有創(chuàng)意的JavaScript小游戲

    12個(gè)非常有創(chuàng)意的JavaScript小游戲

    JavaScript 在Web開發(fā)過程中已經(jīng)是必不可少的重要分子,他推動(dòng)著Web的交互性往越來越高的層次發(fā)展,現(xiàn)在的很多Web游戲也基于這類語言開發(fā)。
    2010-03-03
  • JavaScript字符串分割處理的方法總結(jié)

    JavaScript字符串分割處理的方法總結(jié)

    這篇文章主要介紹了JavaScript字符串分割處理的幾種方法,js截取重要的三要素substring()、subsstr()、slice(),下面文章圍繞這三要素展開全文,需要的小伙伴可以參考一下
    2022-03-03
  • ES6中的Promise對(duì)象與async和await方法詳解

    ES6中的Promise對(duì)象與async和await方法詳解

    Promise是es6引入的異步編程薪解決方案,語法上promise就是一個(gè)構(gòu)造函數(shù),用來封裝異步操作病可以獲取其成功或失敗的結(jié)果,這篇文章主要介紹了ES6中的Promise對(duì)象與async和await方法,需要的朋友可以參考下
    2022-12-12
  • JS實(shí)現(xiàn)仿京東淘寶豎排二級(jí)導(dǎo)航

    JS實(shí)現(xiàn)仿京東淘寶豎排二級(jí)導(dǎo)航

    本文給大家分享一段使用原生Javascript實(shí)現(xiàn)的仿京東淘寶豎排二級(jí)導(dǎo)航的代碼,非常的實(shí)用,有需要的小伙伴參考下
    2014-12-12
  • JS數(shù)組求和的常用方法實(shí)例小結(jié)

    JS數(shù)組求和的常用方法實(shí)例小結(jié)

    這篇文章主要介紹了JS數(shù)組求和的常用方法,結(jié)合實(shí)例形式總結(jié)分析了javascript常見的遍歷、循環(huán)、歸并等數(shù)組操作相關(guān)技巧,需要的朋友可以參考下
    2019-01-01

最新評(píng)論