JS重寫內建 call 方法

2022-09-04 20:09:08 字數 1896 閱讀 5499

let obj = 

function fn(...params)

console.log(fn.call(obj, "引數1", "引數2", "引數n"))// "返回值"

this指向了.call()的第乙個引數。2. 從第二個引數到最後乙個引數,會對 fn 進行傳參。3. 執行函式 fn

let obj = 

function fn(...params)

function.prototype.mycall = function mycall(context, ...params)

// 將來要和原來的 call 方法一樣使用。

fn.mycall(obj, "引數1", "引數2", "引數n")

第一步改變this指向

如果將 fn 變成 obj 的乙個屬性,並呼叫obj.fn(),此時 fn 中的 this 自然指向 obj。

let obj = 

function fn(...params)

obj.fn = fn

obj.fn("引數1", "引數2", "引數n") // 18 "引數1" "引數2" "引數n"

所以,mycall 中可以這樣寫:

let obj = 

function fn(...params)

function.prototype.mycall = function mycall(context, ...params)

fn.mycall(obj, "引數1", "引數2", "引數n") // 18

可以看到,這一步,我們實現了函式 fn 中的 this 指向變為 obj 的功能,並執行了 fn 函式

第二步傳遞引數給 fn

這一步就簡單了,我們可以用 arguments 從下標1開始擷取需要傳遞的引數,也可以和上面的例子一樣,用...params來獲取引數,進行傳遞

let obj = 

function fn(...params)

function.prototype.mycall = function mycall(context, ...params)

fn.mycall(obj, "引數1", "引數2", "引數n") // 18 "引數1" "引數2" "引數n"

看到這一步,基本的 mycall 方法已經完成80%,還有兩個小點要注意:

this 引數可以傳 null,當為 null 的時候,視為指向 window

function.prototype.call = function call(context, ...params) 

let fn = symbol();

context[fn] = this;

context[fn](...params);

delete context[fn]; // 用完記得把新加的屬性刪除掉,不然會越來越。

};

函式 fn 是可以有返回值的!

function.prototype.call = function call(context, ...params) 

let fn = symbol();

context[fn] = this;

let result = context[fn](...params); // 函式執行之後,獲取到返回值。

delete context[fn];

return result // 將獲取到的返回值,返回出去。

};

乙個 模擬 call 方法的 mycall 方法完成。

make內建函式call

在make中,內建函式call用來擴充套件變數或者巨集,它的語法如下 call macro name param1 call會擴充套件它的第乙個引數並把其餘引數依次替換到出現 1 2 的地方,macro name 可以是任何巨集或變數的名稱。macro name之後是巨集的引數,並以逗號為分隔符。c...

js學習總結 call方法深入

var obj function fn fn obj.fn is not a function fn.call obj 首先我們讓原型上的call方法執行,在執行call方法的時候,我們讓fn方法中的this變為第乙個引數值obj 然後再把fn這個函式執行.自己模擬內建的call方法,寫乙個myca...

js陣列內建方法

陣列內建方法 是否修改原陣列 1 棧方法 先進後出 修改 push 進棧 壓棧 pop 出棧 彈棧 彈出乙個資料 2 佇列方法 先進先出 修改 push 進隊 在末尾新增乙個或多個元素 shift 出隊 刪除陣列中第乙個元素 unshift 在陣列頭部新增乙個或多個元素 1.棧方法 var arr ...