面試是一個很好的學習進步的機會,平時咱們老是處於一種安逸的環境看不到本身的不足,面試的過程會把咱們的缺點不斷的暴露,讓你必須不斷的求索。html
一:web
CLI:通用語言基礎結構(Common Language Infrastructure,CLI)是CLR的一個子集,也就是.NET中最終對編譯成MSIL代碼的應用程序的運行環境進行管理的那一部分。在 CLR結構圖中CLI位於下半部分,主要包括類加載器(Class Loader)、實時編譯器(IL To Native Compilers)和一個運行時環境的垃圾收集器(Garbage Collector)。CLI是.Net和CLR的靈魂,CLI爲IL代碼提供運行的環境,你能夠將使用任何語言編寫的代碼經過其特定的編譯器轉換爲 MSIL代碼以後運行其上,甚至還能夠本身寫MSIL代碼在CLI上面運行。面試
CLR:公共語言運行時 (Commen Language Runtime),是一個多語言運行環境,支持衆多的數據類型和語言特性,負責資源管理(內存分配和垃圾收集),保證了應用和底層之間必要的分離。算法
IL: 是.Net平臺的衍生語言,.NET 平臺上面的各類高級語言的編譯器會將各自的文字表達方式轉換成IL。這其中包含了.Net 平臺上面的各類元素,例如 泛型 類 接口 模塊 等等 並且IL 自己並不知道本身是由那種高級語言編譯轉換過來的。數據庫
JIT: JIT(Just In Time簡稱JIT)是.Net邊運行邊編譯的一種機制。 開發人員須要經過IL和CLR進行交流,IL自己支持一些面向對象的概念,可是太過複雜和低效,C# 代碼編譯器會將C#代碼編譯成爲IL,CLR理解IL語言可是CPU只能識別二進制指令,因此JIT會幫助CLR將IL語言編譯成CPU指令。 當.Net 方法被執行時,JIT同步工做數組
GC: 垃圾回收管理 應用程序的內存分配和釋放 運行庫都是從託管推爲新NEW的對象分配內存,垃圾回收器優化引擎根據正在進行的分配狀況肯定執行回收的最佳時間。 當垃圾回收器執行回收是,它會檢查託管堆中再也不有唄應用程序使用的對象並執行必要的操做來回收他們佔的內存資源。安全
二:類和結構的區別 對性能有什麼影響,幾種常見的結構體數據結構
類是引用類型 引用類型在堆上分配地址, 堆棧的執行效率要比堆高,但是堆的資源有限不適合吃力複雜的邏輯對象多線程
結構是值類型,值類型都是在棧上分配地址,值類型將一個變量引用賦值給另一個變量的時候,會複製該結構,所以一個副本的修改不會影響另一條數據架構
.Net BCL 中的結構 :System.Boolean Byte Char Decimal Double Int32 堆棧的空間有限,建立類要比建立結構好一點,大多數狀況這些類型存儲的都是一些數據,因此結構是最佳的選擇
類 : String Object Delegate 接口 等等 包含了大量的邏輯對象,表現抽象
三 :堆 棧
棧 一般保存咱們代碼執行的步驟,而堆存放的多事對象數據等, 棧內存無需咱們管理也不受GC管理,當棧頂元素使用完畢後立馬釋放,而堆存儲的是各類對象的信息,調用完畢後不會被當即清楚,因此須要GC
值類型通常分配在棧上邊 引用類型通常分配在堆上,棧的效率要高於堆。
結構也有可能分配在堆上面,當在類中定義一個結構類型是,該結構就被分配到堆上
四:泛型
泛型的做用是爲了促進代碼的重用,尤爲是算法的重用
優點:可重用性、類型安全、性能上邊避免了Object強制轉換和值類型的裝箱、減小了內存的消耗
.Net BCL 中泛型有 List<T> 經過索引訪問強類型,Dictionary<T> 鍵值對的集合 Quenu<T> 隊列 Stack<T>棧 購物車能夠用Dictionary 查詢結果能夠用List<T>
五:用擴展方法爲C#中的string類型增長一個字符轉換爲數組的方法 和按照字節截取String字符串長度的方法
下邊是按字節長度截取字符串的方法註冊爲String類的擴展方法
public static class StringExt { public static String bSubstring(this string s, int length) { byte[] bytes = System.Text.Encoding.Unicode.GetBytes(s); int n = 0; // 表示當前的字節數 int i = 0; // 要截取的字節數 for (; i < bytes.GetLength(0) && n < length; i++) { // 偶數位置,如0、二、4等,爲UCS2編碼中兩個字節的第一個字節 if (i % 2 == 0) { n++; // 在UCS2第一個字節時n加1 } else { // 當UCS2編碼的第二個字節大於0時,該UCS2字符爲漢字,一個漢字算兩個字節 if (bytes[i] > 0) { n++; } } } // 若是i爲奇數時,處理成偶數 if (i % 2 == 1) { // 該UCS2字符是漢字時,去掉這個截一半的漢字 if (bytes[i] > 0) i = i - 1; // 該UCS2字符是字母或數字,則保留該字符 else i = i + 1; } return System.Text.Encoding.Unicode.GetString(bytes, 0, i); } }
若是最後要截取奇數個字符(以字節爲單位),而且當最後一個字符是字母或數字,則保留該字符,若是是漢字,說明這個漢字被截了一半,則去掉這個漢字。
可使用下面的代碼來截取字符串:
String s = "a加b等於c,若是a等一、b等於2,那麼c等3"; String subStr = s.bSubstring(6); // substr的值是"a加b等"
六:數組 鏈表 hash的區別
程序中存放數據最多見的數據結構就是數組和鏈表,
區別:數組是將數據連續存放的,而鏈表在內存中不是順序存儲的,是經過元素中的指2針聯繫到一塊兒的。
數組是定長的不能適應數據的動態添加,而鏈表是動態分配存儲空間
靜態數組是從棧中分配空間,鏈表從堆中分配空間
在使用時 查詢是數組可以經過下標快速的定位到須要查找的元素,而鏈表則須要從開始一直查找到須要的元素的位置,因此數組的查詢效率要高於鏈表。在進行增長和刪除操做時,數組都須要移動大量的元素來騰出內存空間,而鏈表只須要改變元素中的指針就可實現
而Hash也就是散列則兼備了快速查詢和快速實現增長和刪除的優點,輸入數據經過hash函數可以得到一個Key值,輸入的數據將會存儲到數組中下標爲key的數組單元中去。在實現的過程當中 不一樣的數據可能得到相同的 哈希key值,這時候就產生了hash衝突,而解決hash衝突有兩種方式,一個是創建公共溢出區,講全部產生衝突的數據放到公共溢出區。另一種方式就是 掛鏈式也叫拉鍊式,它的思想就是在產生衝突的hash地址指向一個鏈表,將具備相同key值的數據放到鏈表中。
如何實現hash動態增長空間的效果,這個和裝填因子有密切的關係。 裝填因子=填入表中的數據個數/散列表的長度. 當裝填因子達到必定的值時,咱們講數組增長必定的內存空間,同時reHash.
七:C#中的Invoke和BeginInvoke
Control類實現了ISynchronizeInvoke接口,提供了Invoke和BeginInvoke方法來提供讓其它線程更新GUI界面控件的機制
都須要一個委託對象做爲參數,委託相似於回調函數地址,經過這兩個方法就能夠把須要調用的函數地址推送給界面程序
Invoke 和 BeginInvoke 是爲了解決多線程更新界面顯示的問題,作法是將工做線程中涉及更新界面的代碼封裝成一個方法,用過Invoke 和 BeginInvoke 去調用,二者的區別是Invoke 會致使工做線程的等待,而BeginInvoke 則不會
八:委託是什麼 事件是否是一種委託
委託是一種類型安全的函數指針,將方法做爲參數傳遞 當程序必須調用一個方法來執行某個操做,但編譯器不知道該方法的時候可使用委
託。
事件是一種特殊的委託, 事件的定義
public delegate void EventHandler(object sender, EventArgs e);
常見的各類控件的Click事件的定義: public event EventHandler Click;
PageLoad裏:Button1.Click+=new EventHandler(Button1_Click);
定義Button1的事件 protected Button1_Click(object sender,EventArgs e){}
九:你對IOC的認識 和用過哪些 IOC框架
IOC:Inversion of Control 控制反轉
DI:依賴注入 是一種解耦方式 實現IOC的思想 DI一般有三種 構造器注入 屬性設置注入 接口注入
十:C#常量表達方式ReadOnly和Const的區別
C#的常量分爲兩種 編譯時常量(Const)和運行時常量(ReadOnly)
readOnly 程序運行時賦值 也就是在聲明初始化揮着構造器初始化時賦值,賦值完成後就沒法再更改,也稱只讀變量
const爲編譯時常量,編譯時對常量就行解析,並將多有的常量引用替換爲相應值
十一:數據庫有幾種索引類型,索引的原理和經常使用索引的實現方式
數據庫索引是數據庫管理系統中的一個排序的數據結構,以協助快速查詢和更新數據庫中數據
在常常須要數據搜索的列上加索引,可以加快搜索的速度。常常給WHERE子句上的列增長索引,
對於不常用的列不要添加索引,由於有無索引對查詢的速度沒有太大的影響,
同時索引會佔用物理存儲空間,對於只有不多數組的列也不須要添加索引,如性別列,在查詢結果中結果集中的數據表佔據了數據表中的很大比例,增長索引並不會明顯提升查詢速度。
同時對於數據類型爲 text bit image 的數據類型字段不該該增長索引,這些字段要麼數據兩太大,要麼取值太少。
當修改性能遠大於檢索性能的時候也不該該創建索引, 這是由於修改性能和檢索性能是相互矛盾的, 修改性能在修改數據的同時 還要修改數據庫的索引。
按照數據庫的功能,能夠在數據庫中設計三種索引,惟一索引 主鍵索引和彙集索引
惟一索引不容許其中任何兩行具備相同的值
主鍵索引 在數據庫關係表中建立主鍵會默認建立主鍵索引 主鍵索引是索引的特定類型,該索引要求主鍵中的每一個值都惟一
彙集索引 中表中行的物理順序和鍵值的索引順序相同,一張表中只能有一個彙集索引
十二 什麼是NOSQL NOSQL的優點是什麼
NOSQL 即 NOT Only SQL
NOSQl種類不少,NoSQL被咱們用得最多的當數key-value存儲,固然還有其餘的文檔型的、列存儲、圖型數據庫、xml數據庫等。在NoSQL概念提出以前,這些數據庫就被用於各類系統當中,可是卻不多用於web互聯網應用。好比cdb、qdbm、bdb數據庫。
NOSQL去掉關係型數據庫特性,數據庫之間無關係這樣就很是容易擴展,也在無形之間在架構層面帶來了可擴展的能力,NOSQL還具備很是強的讀寫能力,這得益於它的無關係性,數據庫的結構簡單,NOSQL無需事先爲要儲存的數據創建字段,隨時能夠自定義數據格式,而在傳統關係型數據中,數據庫字段的增刪字段尤爲是增長字段是一件很麻煩的事情。
高可用
NoSQL在不太影響性能的狀況,就能夠方便的實現高可用的架構。好比Cassandra,HBase模型,經過複製模型也能實現高可用。
附錄 常見的NOSQL數據庫
十四:適用迭代器 yield關鍵字
迭代器是一個連續的集合,出現多個 yield return 其實就是將多個yield return 元素按照出現的順序存儲在迭代器的集合中。
/// <summary> /// 迭代器方法 /// </summary> static IEnumerable Documents(List<string> docs) { foreach (string s in docs) { yield return s; } }
上邊實現迭代器的方法,調用迭代器
十五:lock
當咱們使用線程的時候,效率最高的方式固然是異步,即各個線程同時運行,其間不相互依賴和等待。但當不一樣的線程都須要訪問某個資源的時候,就須要同步機制了,也就是說當對同一個資源進行讀寫的時候,咱們要使該資源在同一時刻只能被一個線程操做,以確保每一個操做都是有效即時的,也即保證其操做的原子性。lock是C#中最經常使用的同步方式,格式爲lock(objectA){codeB} 。
lock不能鎖定值類型,lock的參數若是是值類型的話勢必會發生裝箱操做,這樣每次lock的都是一個新的對象。一般最好避免public類型或者不受控制的對象實例,若是該是咧能夠被公開訪問
十六:WebService WCF WebApi
WebService 和 WCF 都是基於SOAP協議的,數據格式都是XML,而且都不是開源的,不一樣之處在於WebService只支持Http協議且只能部署在IIS上,WCF相對來說配置更加的繁瑣可是可以支持TCP HTTP HTTPS Named ...... 而且能夠部署在應用程序中 、IIS、Windows服務中。
WebApi是一個輕量級的框架,對移動端的支持比較好。是一個開源的基於Rest-Full的,它繼承了HTTP的所有特色,同時支持MVC特性,如路由 控制器 Action 模型綁定 控制反轉(IOC) 依賴注入(DI) 單元測試 這樣使程序更加的健壯,它能夠配置在應用程序和IIS中。