C#語言基礎常見問題匯總

來源:互聯網
上載者:User
概述

1. 什麼是C#?

C#是Microsoft公司設計的一種程式設計語言。它鬆散地基於C/C++,並且有很多方面和Java類似。

Microsoft是這樣描述C#的:“C#是從C和C++派生來的一種簡單、現代、物件導向和型別安全的程式設計語言。C#(讀做‘Csharp’)主要是從C/C++程式設計語言家族移植過來的,C和C++的程式員會馬上熟悉它。C#試圖結合Visual Basic的快速開發能力和C++的強大靈活的能力。”

2. 如何開發C#應用程式?

.NET SDK包括了C#命令列編譯器(csc.exe),下一個版本的Visual Studio (Visual Studio 7 or Visual Studio.NET)會包含對C#開發的完整支援。

3. C#可以取代Java?

C#非常像Java語言——這兩種語言的核心和C++相比都有相似的優缺點。例如,兩個語言都有記憶體回收,但是兩個語言都沒有模板(template)。Microsoft已經中止了Visual J++產品,因此很難不認為Microsoft在使用C#來替代Java。

4. C#可以取代 C++?

顯然是不,但是我們又很難說C++是新的.NET平台上編寫代碼的最佳選擇。為了使.NET的運行層能完全發揮作用,它要求程式設計語言遵循某些特定的規則——其中之一就是所有的語言類型必須遵守一般型別系統(Common Type System,CTS)。不幸的是,許多C++特性不能被CTS支援。例如,模板和類的多重繼承。

專業的3S站 3s8.cn

Microsoft對這個問題的答案是給C++提供可管理的擴充(Managed Extensions,ME), 這可以使C++遵守CTS。通過添加新的關鍵字來標記C++類有CTS的屬性(例如.-gc表示記憶體回收)。但是在建立新的工程時很難講為什麼ME C++會比C#更合適。就特徵(feature)而言它們很相似,但與C++不同的是C#從一開始就以.NET為環境設計的。ME C++存在的理由好像是將C++代碼移植(port)為.NET環境下的代碼。

因此,這個問題的答案,很可能是C++作為一個.NET環境之外的語言將依然保留它的重要性;而通過ME將現存的C++代碼移植為適合.NET環境;但是很可能C#將是C++開發人員開發新的.NET應用程式的最好選擇。

8. C#是物件導向的嗎?

是的,C#像Java和C++一樣,是一個物件導向的語言。

9. C#有自己的類庫嗎?

不,就像所有的.NET語言(VB.Net,JScript .Net...)一樣,C#訪問.NET類庫,C#沒有自己的類庫。

基本類型

1. C#提供什麼標準類型?

C# 支援的基本類型和C++很相似,包括int, long, float, double, char, string, arrays, structs 和 classes。然而,不要假設太多,名字可能很形似,但是一些細節不相同。例如C#中的long是64位的,而C++的long取決於平台,32位的平台上是32位的,64位的平台上是64位的。class和struct在C++中幾乎完全一樣,但在C#中並不是這樣的。

專業的3S站 3s8.cn

2. 是否所有的C#類型都派生於一個公用的基類?

是,也不是,所有的對象都可以看作從Object (System.Object)派生而來。但是為了把像int,float這樣的實值型別執行個體看作是從Object對象派生的,這個執行個體必須通過一個裝箱的操作(boxing)轉化為參考型別。理論上,開發人員可以忽略這些底層的轉化,但是認識到這點對於系統效能影響很重要。

3. 是否可以這樣認為,可以將一個實值型別的執行個體作為參數傳給以對象為參數的方法?

是的,例如:

class CApplication {

public static void Main() {

int x = 25;

string s = “fred”;

DisplayMe( x );

DisplayMe( s ); }

static void DisplayMe( object o ) {

System.Console.WriteLine( “You are {0}”, o ); }}

將顯示:

You are 25

You are fred
4. 實值型別和參考型別的最基本的區別是什嗎?

C#將類型分為兩類,一類是實值型別,另一類是參考型別。大部分固有的基本類型(如int, char)是實值型別,structs 也是實值型別。參考型別包括類、介面、數組和字串。基本的概念非常簡單,那就是一個實值型別的執行個體代表了實際的資料(存在棧中),而一個參考型別的執行個體代表指向資料的指標或者引用(存在堆中)。

C++開發人員最容易混淆的地方是:C#已經自己預定義了一些類型作為實值型別,一些作為參考型別,而一個C++的開發人員希望能夠自己控制。

例如,在C++中,我們可以這樣做:

int x1 = 3; // x1 是堆棧上的值

int *x2 = new int(3) // x2 是堆的一個值的引用

但是在C#中沒有這樣的控制:

int x1 = 3; // x1是堆棧上的值

int x2 = new int();

x2 = 3; // x2還是堆棧上的值!

5. 既然 int是實值型別,而 class是參考型別,那麼int是怎樣從Object派生的呢?

是這樣的,當int用作int時候,這是一個實值型別(在棧上),然而,當它用作是Object時,這是一個引用堆上的整數值的參考型別。換而言之,當你將int看作對象時,運行層將它自動轉化為對象引用,這個轉化過程稱作裝箱(boxing)。這個轉換包括將棧裡的值拷貝到了堆裡,並且建立了一個對象的執行個體來引用該值。拆箱操作(unboxing)是個反過程——將對象轉化為基於棧的實值型別。

中國3S吧 3s8.cn

int x = 3;

// 堆棧上新的int類型,值為3

object objx = x;

// 堆上新的int, 設定值為3,x=3仍然在堆棧上

int y = (int)objx;

//新的int類型的值3在堆棧上,x=3在堆棧上,objx=3在堆上

6. C#使用引用替代指標,那麼C#的引用和C++的引用一樣嗎?

不完全,基本的思想是一樣的,但是一個重要的區別是C#的引用可以是null。因此你不能確認C#的引用一定會是一個有效對象。如果試圖使用一個值為null的引用,一個NullReferenceException 異常將被拋出。

例如,看一看以下的方法:

void displayStringLength( string s ) {

Console.WriteLine( “String is length {0}”, s.Length ); }

如果這樣調用它,這種方法將產生一個NullReferenceException 異常:

string s = null;

displayStringLength( s );

當然有些情況你認為產生這樣一個異常是完全可以接受的結果,但是在這個例子裡最好按下面的代碼改寫一下:

中國3S吧 3s8.cn

void displayStringLength( string s ) {

if( s == null )

Console.WriteLine(“String is null”);

else

Console.WriteLine(“String is length {0}”, s.Length );

}
class和struct

1. struct在C++中是多餘的,為什麼C#還要使用它們呢?

在C++中,一個結構和一個類幾乎就是一個同樣的東西。唯一的區別是預設的成員的存取層級不一樣(struct的預設層級是public,class的預設層級是private)。然而,在C#中struct和class完全不一樣。在C#中,struct 是實值型別,而class是參考型別。另外struct不能從其他struct或者class繼承,儘管struct可以實現介面。struct沒有析構器。

2. C#支援多重繼承嗎?

C#支援介面的多重繼承,但是不支援類的多重繼承。

3. C#介面和C++抽象類別一樣嗎?

不,不完全。C++的抽象類別不能被執行個體化。但是它可以(而且經常是)包含執行代碼和資料成員。一個C#介面不能包含任何執行代碼或資料成員,它只是一組方法名稱和簽名(signature)。一個C#的介面更像是一個COM介面而不是抽象類別。

另一個主要的不同點是:C#類只能從一個類(不管是否抽象)繼承,但可以實現多重介面。

4. C#構造器和C++ 構造器是否相同?

非常相似,但是它們絕對不同。第一,C#析構器不保證在某個特定的時間被調用。實際上它根本不保證被調用。真實的情況是,C#析構器只是一個偽裝了的Finalize方法。具體點講,它是一個插入調用基類Finalize方法的Finalize方法。因此,這段代碼:

專業的3S站 3s8.cn

class CTest {

~CTest() {

System.Console.WriteLine(“Bye bye” );

}

}

實際上就是:

class CTest {

protected override void Finalize() {

System.Console.WriteLine(“Bye bye” );

base.Finalize();

}

}

如果你不相信,可以將一個 Finalize方法和一個析構器加入C#類中,然後就可以知道是如何編譯的了。

5. 什麼是靜態構造器?

它是整個類的一個構造器,而不是類的一個執行個體的構造器,它在類裝載的時候被調用。

6. C#中所有的方法都是虛方法嗎?

不,像C++一樣,預設的時候,方法不是虛擬,但都可以改為虛擬。

7. 怎樣在C#中聲明一個純虛函數?

在方法前使用abstract修飾符,類也可以標記為abstract(這是自然的)。注意,abstract方法不能有執行代碼(不同於C++中純虛方法)。

中國3S吧 3s8.cn

和C++處理的不同

1. 我“new”了一個對象,但是我怎樣刪除它?

你不能,不允許你顯式地調用析構器,也沒有delete操作符。但是不必擔心,記憶體回收(garbage collection)會釋放你的對象,最終會的(也許會的)。

2. 我試圖在棧上建立一個對象,但是C#編譯器不通過,這是怎麼回事?

和C++不同,你不能在棧上建立一個對象的執行個體。類的執行個體總是被建立在堆上並且接受記憶體回收行程(garbage collection)的管理。

3. 我定義了一個析構器,但是它從來不能被調用,為什麼?

一個C#析構器實際上是Finalize方法的實現,但是運行環境不保證調用Finalize方法。你可以考慮通過調用GC.RequestFinalizeOnShutdown()方法試一下。

4. 大多數的C#基本類型和C++的基本類型有相同的名字,它們一樣嗎?

不,C#中char和C++中的wchar是相同的。C#中所有的字元包括字串都是Unicode的,C#中整型值是固定大小的,而在C++中其大小取決於處理器。例如,一個C#的int是32位的,而C++ 中int在32-bit處理器上是32位的,在64-bit處理器上是64位的,一個C#的long是64位的。

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.