我正在學習Javascript,並且我已經閱讀函數是第一類對象,大多數作者提到函數可以返回函數(它們是對象)並將它們作爲參數傳遞給其他函數。C#和Javascript中的函數之間的區別?
我相信還有更多的東西,所以C#中的函數和javascript中的函數有什麼區別?我有權利說函數不是對象(不具有方法,屬性等),即使使用閉包(使用lambda表達式和委託),它們看起來像JavaScript中的函數對象一樣嗎?
我覺得在C#中使用lambda表達式的區別對於剛剛學習語言的人來說有點模糊。
我正在學習Javascript,並且我已經閱讀函數是第一類對象,大多數作者提到函數可以返回函數(它們是對象)並將它們作爲參數傳遞給其他函數。C#和Javascript中的函數之間的區別?
我相信還有更多的東西,所以C#中的函數和javascript中的函數有什麼區別?我有權利說函數不是對象(不具有方法,屬性等),即使使用閉包(使用lambda表達式和委託),它們看起來像JavaScript中的函數對象一樣嗎?
我覺得在C#中使用lambda表達式的區別對於剛剛學習語言的人來說有點模糊。
的一個最大的區別我能想到的是,在C#中的函數,變量是詞彙作用域確定,而JavaScript中,變量都是局部的除了爲this
,這是動態作用域。
例如,在Javascript中,你可以這樣說
var foo = new Object();
foo.x = 0;
var bar = function() { this.x = 2; }; // first-class function... what's "this"?
foo.baz = bar; // Now foo has a method called 'baz', which is 'bar'.
foo.baz();
alert(foo.x); // Displays 2 -- 'this' magically refers to 'foo'!
嘗試在C#寫的。或者實際上,不要打擾 - 這不會有任何意義。
爲什麼?因爲this
這裏沒有提到任何東西,詞法!它的含義動態變化,與C#不同,它的含義僅取決於封閉類,而不是調用者實際是誰。
你有這個錯誤。函數中使用的變量(使用任何編程語言)可以是自由的(非本地的)或綁定的(本地的)。在詞彙範圍的語言中,當__it被定義時,函數的自由變量被解析爲函數父範圍中的變量。在動態範圍的語言中,當__it被調用___時,函數的自由變量被解析爲函數調用範圍中的變量。 'this'關鍵字不是一個自由變量。它有特殊的規則。請參閱以下[問題](http://stackoverflow.com/q/10060857/783743「動態範圍」。)。 –
@AaditMShah:呃,不,我確定這是正確的......不確定你說的哪一部分是「錯誤的」,但正如我剛纔提到的,'this'是動態範圍的JS,並且其他變量是靜態範圍的。我也不知道這裏的自由與綁定變量是什麼意思,因爲我沒有看到除'this'之外的任何「自由」變量,我已經提到這個變量是動態變量。 – Mehrdad
謝謝,真的很有趣...甚至沒有意識到動態範圍。 –
大多數作者說的是「功能是first class公民」在JavaScript中。它們分別是而不是 C#中的第一類,它們只是方法那裏,附屬於一個類。方法代表(和lambda)是爲了製作方法如頭等公民的具體類。
因此,這裏的東西,盡我所能解釋,沒有告訴你回去和閱讀Crockford的「使用Javascript:好的部分」,並像飛碟雙向某人或某物:
JavaScript有少了很多零件比C#。不要把你可以在C#中直接做的事情與你可以(或不能)在Javascript中做的事情(也可以不做)進行比較。
那麼爲什麼不是所有的語言(或至少C#)都有「頭等功能」?答案通常最簡單:因爲這不是語言設計要求。然而,這是我的一個陰謀,因爲顯然他們現在已經加入了它。但是如果沒有人告訴你以你的未來語言包含它,你會嗎?
所以要記住的關鍵是:在C#函數(方法)必須附加到類。在Javascript中他們沒有。原因在於語言定義(spec)。
您可以通過以下兩種方式之一在JavaScript中創建一個新的對象:
//using object syntax
var ob1 = { name: value, nestedFunction: function(){} };
或
//using a function
function MyFunc(){
var name = value;
function nestedFunction(){}
}
var ob2 = new MyFunc();
另外,我應該在對象創建語句跟進
而在第二種情況下,我們使用一個函數來聲明對象,在第一種情況下,我們只是使用文字語法來聲明它。
要做到在C#同樣的事情,我們必須創建一個新的對象爲一類:
MyClass ob1 = new MyClass(); //constructor is a member function of the class
public class MyClass {
public MyClass() {
}
public void nestedFunction(){
}
}
請注意,在JavaScript的一個我仍然有定義正在返回的方法。
好吧,我覺得今晚就夠了。
我會乞求不同...'Predicate
它仍然是一個'Predicate
你不能在C#中執行閉包嗎?對不起,但是... wtf? – Mehrdad
Javascript函數可以創建並分配給一個變量,它們是語言中的第一類公民,並且對C#應用的語法糖具有一定的靈活性。
在C#中,當你寫的代碼
x => x * x
編譯器創建一個名爲實際方法和包裝該方法在delegate
可以執行。
代表以及C#應用的語法糖給人一種非常類似於JavaScript的感覺,但它在內部做着非常不同的事情。
在JavaScript中,您可以創建一個函數並將其直接分配給一個變量並執行它,而不用將其包裝在任何其他結構中以啓用該操作。函數是JavaScript中的一等公民。
在C#中,編譯器並沒有那麼做。你也需要提到的委託類型。 :-) – Mehrdad
當可用時,它將使用從上下文推斷的委託類型。這可以歸結爲語法糖。 –
我對JS和C#的區別一些粗略的想法:
1,JS是一種解釋型語言,這意味着JS需要一個瀏覽器內置的ECMAScript的解釋工作。而C#是一種編譯語言,這意味着C#代碼將被編譯爲IL來工作。
2,JS是一種動態類型語言,這意味着您在定義時不需要指定變量的類型。而C#是靜態類型語言,這意味着您需要指定變量的確切類型。
3,OOP封裝,在JS中,很多人都說功能是一等公民。通常情況下,函數有兩種用法:a)只是一個函數來操縱一些工作b)類&構造函數,使用它可以實例化對象。而在C#中,函數是函數,它應該屬於類(或接口)。
4,OOp繼承,在JS中,我們用原型來實現繼承。而在C#中,我們嚴格使用類來實現繼承。根據我的知識,我們可以使用參數,這是一個僞數組,用來實現模擬多態的功能重載,這是一個瘀傷。而對於C#來說,多態是如此完美的體現。
6,在JS中,我們沒有GC。而C#有一個強大的GC。
也許有些想法是不正確的,歡迎提出建議。
問題是關於C#和Javascript *函數*之間的語義差異 - 不是兩者作爲*語言*的區別列表。 –
只是爲了澄清一些混淆;
1)JavaScript確實是一種編譯語言。代碼編譯的方式就在瀏覽器執行之前,而且速度很快!這就是爲什麼有些開發人員認爲這是一種「解釋性」語言。
2)C#沒有JS意義上的函數。它有類方法。
C#甚至沒有函數*本身* - 它只有方法(和委託/ lambdas,這是方法引用)。也就是說,你可以調用代表C#模擬JavaScript匿名函數對象。 – BoltClock
@BoltClock:功能與方法與程序與子程序與任何...我真的沒有看到它們之間的差異,如果不是更多... – Mehrdad
@Mehrdad:是啊... :) – BoltClock