天天看點

javascript的call和apply

coffeescript裡,每個檔案編譯成JS後,都是(function(){...}).call(this);的架勢

這個call,該怎麼了解呢?

在javascript裡面,call 或者 apply 用于使并未定義某個函數的對象也可以使用該函數。換言之,它擴充了該對象,讓它忽然多了一個函數。call與apply的差別,僅僅在于參數的形式。

function sayHello(sentence){
  alert(sentence);
}
function leftfist(){}
sayHello.call(leftfist,"Hello World!");
sayHello.apply(leftfist,["Hello World!"]);      

大概,這就是所謂的文法糖吧?網上的文章都說得很複雜,什麼改變運作對象,上下文之類,這當然沒有錯,但我認為這會越說越複雜,越說越玄虛,無助于了解本質。不及我這個例子那麼直達本質。CoffeeScript裡這個編譯後的call(this),倒真的是為了限定上下文。

在C#裡面,也有類似的功能。它可以很友善地擴充一個現有類的功能,而不會引起已有代碼的編譯錯誤或什麼變化。新加的功能,完全是額外贈送的,差不多二次開發的性質。

它就是this參數。

沒代碼我說個J8。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace ConsoleApplication1
{
    using CustomExtensions;
    class Program
    {
        static void Main(string[] args)
        {
            string str = "leftfist";
            Console.WriteLine(str.HelloWorld());
            Console.Read();
        }
    }
}
namespace CustomExtensions
{
    public static class StringExtensions
    {
        public static string HelloWorld(this string str)
        {
            StringBuilder sb = new StringBuilder(str);
            sb.Append(">Hello World!");
            return sb.ToString();
        }
    }
}      

上述代碼中,string憑空獲得了一個函數:HelloWorld()。