javacscript apply and call
call方法:
語法:a.call(b,param1,param2.....paramN);
說明:a 方法,b方法,param1,param2.....paramN 為a方法的引數,引數可以有多個也可以沒有,多個引數用逗號隔開。
apply方法:
語法:a.apply(b,[param1,param2....paramN])
說明:a 方法,b方法,[param1,param2.....paramN] 為a方法的引數,引數可以有多個也可以沒有,必須以陣列的形式。
call和apply方法相同,只不過傳引數的方法不同,a、b兩個方法相當於繼承,a像父類,b像子類,b有a的所有方法。
call && apply
<!--
function a(name,age){
this.name=name;
this.age=age;
this.showName=function(){
alert(this.name);
}
}
function b(dep){
this.dep=dep;
}
var c = new b("English!!!")
//a.call(c,"black cat",19);
a.apply(c,["black cat",19]);
c.showName();
alert(c.dep);
// -->
看javascript的call 和apply的用法 收藏
本來是想在這裡寫寫call 和apply的用法,但是我剛在網上看到一篇討論,感覺比較講得徹底,拿過來吧 ,自己又懶了一把,
function foo(x) {
this.x = x;
var y = "Just a y";
}
function bar(foo) {
return function() {
var temp = {};
foo.apply(temp, arguments);
alert("In bar now");
alert("temp.foo:" + temp.foo + "\n" +
"temp.x:" + temp.x + "\n" +
"temp.y:" + temp.y);//注意看這一行的執行結果
}
}
var func = bar(foo);
func("In foo now");
試驗結果表明:apply以後,temp物件就繼承了foo類的公有變數了。也就是說,這一句 foo.apply(temp, arguments);實際上就是把foo()函式當成temp物件的建構函式來呼叫了。一旦構造完畢,temp物件就具有了成員this.x。
這樣,我有了兩種理解方案:
①按照傳統的物件導向的語言來理解:一般來說,建構函式是不能被外界(不包括派生類)訪問的。因此,這句話“呼叫apply時,是把foo函式變成temp物件的方法,然後呼叫”是正確的,而“可是temp.foo竟然沒有定義”則是理所當然的事情了。
②按照JavaScript語言自身的物件機制來理解:在JavaScript中,(構造 )函式就是國王、一等公民,它就是類就是它。物件則是(構造)函式的例項。因此,通過物件來訪問建構函式,顯然是行不通的。
其實,說構造未必準確(但我們可以利用建構函式來理解這個處理過程),我認為應該說成克隆,也就是說系統把foo類擁有的所有公有變數複製給了temp物件(這裡是指Object,Function,Array和包裝型物件“四類”物件)。
藍色的文字表明,如果temp不是一個物件型(指以上提到的四類物件)變數的話,克隆過程就不會發生,如下所示:
foo.apply(0, arguments);
foo.apply(null, arguments);
foo.apply(undefined, arguments);
foo.apply(true, arguments);
foo.apply("hello,world", arguments);
foo.apply({}, arguments);
那麼foo.apply()實際上就和普通的方法呼叫沒有什麼區別了,只是有了它,我們可以利用傳遞arguments引數的便利。
所以,apply(和call)的應用場合就浮現出來了:
①我們需要把一個類的公有變數複製給另一個物件。
②我們要快速而“智慧”的傳參,而不是手動去書寫arguments[0],arguments[1]...
問一個函式與函式之間傳引數的問題,我覺得我這種方法太麻煩,不知道大家還有沒有更好的方法.
如果按傳統的方式來,得這樣寫:
function user( ) {
test(arguments[0], arguments[1]);
}
function test(id,name) {
alert(id +"-----------"+name);
}
user("dfdfd","kkkkk");
這樣寫的缺點很明顯,萬一引數一變,程式就掛了。
而利用apply,程式就變聰明多了:
function user( ) {
test.apply(0, arguments);
}
function test(id,name) {
alert(id +"-----------"+name);
}
user("dfdfd","kkkkk");
apply(...)和call(...)確實很實用,比如實現一個類建立模式
<!--
var Class = {
create: function() {
return function() {
this.initialize.apply(this, arguments);
}
}
};
var vehicle = Class.create();
vehicle.prototype = {
initialize: function(type){
this.type=type;
},
showSelf: function(){
alert("this vehicle is "+ this.type);
}
};
var moto=new vehicle("Moto");
moto.showSelf();
//-->
一個跨框架呼叫的例子
在View框架中有三個測試button,點選分別對應三種呼叫方式,第一種是通過最原始的obj.fn()來呼叫Controller框架中的fn函式,第二種是比較原始的eval拼裝arguments跨框架字串,第三種是改寫的apply方法應用~
/**
* index.htm
*/
測試跨框架呼叫-apply()應用
UnSupport Frame. Structure!
/**
* view.htm
*/
:::View:::
<!--
// Cross Frames Function
var fFunc = function(){
try{
var iLen = arguments.length;
if(iLen == 0) return;
else{
var sFuncStr = "top.frames['js_frame'].";
sFuncStr += arguments[0] + "(";
for(var i=1; i sFuncStr += "'" + arguments[i] + "',";
}
sFuncStr = sFuncStr.substring(0, sFuncStr.length-1);
sFuncStr += ");";
eval(sFuncStr);
}
}
catch(ex){
window.alert("Error: " + ex.description);
}
};
// Cross Frames Function Apply
var fGoto = function(){
try{
var sFuncStr = "top.frames['js_frame'].";
var arr = [];
for(var i=0; i arr[i] = arguments[i];
}
arr = arr.slice(1);
var func = eval(sFuncStr + arguments[0]);
func.apply(window, arr);
}
catch(ex){
window.alert("Error: " + ex.description);
}
};
//-->
/**
* controller.htm
*/
:::Controller:::
<!--
function fTest(sStr1, sStr2){
window.confirm(sStr1);
window.alert(sStr2);
}
//-->
提一點建議。。。利用apply的那一個函式可以優化如下:
// Cross Frames Function Apply
var fGoto = function(){
try{
var arr = [];
for(var i=0; i arr[i] = arguments[i];
}
arr = arr.slice(1);
parent.frames['js_frame'][arguments[0]].apply(0, arr);
}
catch(ex){
window.alert("Error: " + ex.description);
}
};
語法:a.call(b,param1,param2.....paramN);
說明:a 方法,b方法,param1,param2.....paramN 為a方法的引數,引數可以有多個也可以沒有,多個引數用逗號隔開。
apply方法:
語法:a.apply(b,[param1,param2....paramN])
說明:a 方法,b方法,[param1,param2.....paramN] 為a方法的引數,引數可以有多個也可以沒有,必須以陣列的形式。
call和apply方法相同,只不過傳引數的方法不同,a、b兩個方法相當於繼承,a像父類,b像子類,b有a的所有方法。
function a(name,age){
this.name=name;
this.age=age;
this.showName=function(){
alert(this.name);
}
}
function b(dep){
this.dep=dep;
}
var c = new b("English!!!")
//a.call(c,"black cat",19);
a.apply(c,["black cat",19]);
c.showName();
alert(c.dep);
// -->
看javascript的call 和apply的用法 收藏
本來是想在這裡寫寫call 和apply的用法,但是我剛在網上看到一篇討論,感覺比較講得徹底,拿過來吧 ,自己又懶了一把,
function foo(x) {
this.x = x;
var y = "Just a y";
}
function bar(foo) {
return function() {
var temp = {};
foo.apply(temp, arguments);
alert("In bar now");
alert("temp.foo:" + temp.foo + "\n" +
"temp.x:" + temp.x + "\n" +
"temp.y:" + temp.y);//注意看這一行的執行結果
}
}
var func = bar(foo);
func("In foo now");
試驗結果表明:apply以後,temp物件就繼承了foo類的公有變數了。也就是說,這一句 foo.apply(temp, arguments);實際上就是把foo()函式當成temp物件的建構函式來呼叫了。一旦構造完畢,temp物件就具有了成員this.x。
這樣,我有了兩種理解方案:
①按照傳統的物件導向的語言來理解:一般來說,建構函式是不能被外界(不包括派生類)訪問的。因此,這句話“呼叫apply時,是把foo函式變成temp物件的方法,然後呼叫”是正確的,而“可是temp.foo竟然沒有定義”則是理所當然的事情了。
②按照JavaScript語言自身的物件機制來理解:在JavaScript中,(構造 )函式就是國王、一等公民,它就是類就是它。物件則是(構造)函式的例項。因此,通過物件來訪問建構函式,顯然是行不通的。
其實,說構造未必準確(但我們可以利用建構函式來理解這個處理過程),我認為應該說成克隆,也就是說系統把foo類擁有的所有公有變數複製給了temp物件(這裡是指Object,Function,Array和包裝型物件“四類”物件)。
藍色的文字表明,如果temp不是一個物件型(指以上提到的四類物件)變數的話,克隆過程就不會發生,如下所示:
foo.apply(0, arguments);
foo.apply(null, arguments);
foo.apply(undefined, arguments);
foo.apply(true, arguments);
foo.apply("hello,world", arguments);
foo.apply({}, arguments);
那麼foo.apply()實際上就和普通的方法呼叫沒有什麼區別了,只是有了它,我們可以利用傳遞arguments引數的便利。
所以,apply(和call)的應用場合就浮現出來了:
①我們需要把一個類的公有變數複製給另一個物件。
②我們要快速而“智慧”的傳參,而不是手動去書寫arguments[0],arguments[1]...
問一個函式與函式之間傳引數的問題,我覺得我這種方法太麻煩,不知道大家還有沒有更好的方法.
如果按傳統的方式來,得這樣寫:
function user( ) {
test(arguments[0], arguments[1]);
}
function test(id,name) {
alert(id +"-----------"+name);
}
user("dfdfd","kkkkk");
這樣寫的缺點很明顯,萬一引數一變,程式就掛了。
而利用apply,程式就變聰明多了:
function user( ) {
test.apply(0, arguments);
}
function test(id,name) {
alert(id +"-----------"+name);
}
user("dfdfd","kkkkk");
apply(...)和call(...)確實很實用,比如實現一個類建立模式
<!--
var Class = {
create: function() {
return function() {
this.initialize.apply(this, arguments);
}
}
};
var vehicle = Class.create();
vehicle.prototype = {
initialize: function(type){
this.type=type;
},
showSelf: function(){
alert("this vehicle is "+ this.type);
}
};
var moto=new vehicle("Moto");
moto.showSelf();
//-->
一個跨框架呼叫的例子
在View框架中有三個測試button,點選分別對應三種呼叫方式,第一種是通過最原始的obj.fn()來呼叫Controller框架中的fn函式,第二種是比較原始的eval拼裝arguments跨框架字串,第三種是改寫的apply方法應用~
/**
* index.htm
*/
UnSupport Frame. Structure!
/**
* view.htm
*/
<!--
// Cross Frames Function
var fFunc = function(){
try{
var iLen = arguments.length;
if(iLen == 0) return;
else{
var sFuncStr = "top.frames['js_frame'].";
sFuncStr += arguments[0] + "(";
for(var i=1; i
}
sFuncStr = sFuncStr.substring(0, sFuncStr.length-1);
sFuncStr += ");";
eval(sFuncStr);
}
}
catch(ex){
window.alert("Error: " + ex.description);
}
};
// Cross Frames Function Apply
var fGoto = function(){
try{
var sFuncStr = "top.frames['js_frame'].";
var arr = [];
for(var i=0; i
}
arr = arr.slice(1);
var func = eval(sFuncStr + arguments[0]);
func.apply(window, arr);
}
catch(ex){
window.alert("Error: " + ex.description);
}
};
//-->
/**
* controller.htm
*/
<!--
function fTest(sStr1, sStr2){
window.confirm(sStr1);
window.alert(sStr2);
}
//-->
:::JS Frame.:
提一點建議。。。利用apply的那一個函式可以優化如下:
// Cross Frames Function Apply
var fGoto = function(){
try{
var arr = [];
for(var i=0; i
}
arr = arr.slice(1);
parent.frames['js_frame'][arguments[0]].apply(0, arr);
}
catch(ex){
window.alert("Error: " + ex.description);
}
};
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/25897606/viewspace-704293/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- this、apply、call、bindAPP
- this、call和applyAPP
- Javascript - apply、call、bindJavaScriptAPP
- this, call, apply 和 bindAPP
- apply & call & bind 原始碼APP原始碼
- bind/call/apply 深度理解APP
- 手寫call,apply,bindAPP
- apply,call,bind的用法APP
- 新手理解 apply 和 callAPP
- call、apply、bind 區別APP
- apply call bind 簡介APP
- 手寫call、apply、bindAPP
- this指向與call,apply,bindAPP
- call apply bind區別APP
- js中的call、applyJSAPP
- JavaScript-apply、bind、callJavaScriptAPP
- JavaScript中的call()和apply()JavaScriptAPP
- [譯] Javascript: call()、apply() 和 bind()JavaScriptAPP
- JavaScript重識bind、call、applyJavaScriptAPP
- 一個例子看懂call,applyAPP
- JavaScript 中的 apply、call、bindJavaScriptAPP
- JS中的call、apply、bindJSAPP
- js call,apply,bind總結JSAPP
- 【筆記】apply, call 與 bind筆記APP
- call,apply,bind,new實現原理APP
- 模擬實現apply/call/bindAPP
- call.apply.bind 走一個!APP
- call,apply和bind的區別APP
- 一文搞懂 this、apply、call、bindAPP
- js call、apply、bind的實現JSAPP
- 詳解 JavaScript的 call() 和 apply()JavaScriptAPP
- bind,call,apply模擬實現APP
- JS中的call、apply、bind方法JSAPP
- javascript -- apply/call/bind的區別JavaScriptAPP
- 為什麼 call 比 apply 快?APP
- 深入理解JS的apply()、call()JSAPP
- JS中的call()和apply()方法JSAPP
- js中call、apply、bind函式JSAPP函式