1、什麼是反射:
Reflection,中文翻譯為反射。
這是.Net中獲取運行時類型資訊的方式 ,.Net的應用程式由幾個部分: '組件(Assembly)'、'模組(Module)'、'類型(class)'組成,而反射提供一種編程的方式,讓程式設計師可以在程式運行期獲得這幾個組成部分的相關資訊。
反射的概述
反射的定義:審查元資料並收集關於它的類型資訊的能力 。元資料(編譯以後最基本的資料單 元)就是一大堆的表,當編譯組件或模組時,編譯器會建立一個類別定義表,一個欄位定義表,和一個方法定義表等。 System.reflection命名 空間包含的幾個類,讓你可以反射(解析)這些元資料表的程式碼。
2、反射的具體用途:
(1)使用Assembly定義和載入程式集,載入在程式集清單中列出模組,以及從此程式集中尋找類型並建立該類型的實例。
(2)使用 Module了解包含模組的組件以及模組中的類別等,還可以取得在模組上定義的所有全域方法或其他特定的非全域方法。
(3)使用 ConstructorInfo來了解建構子的名稱、參數、存取修飾符(如pulic 或private)和實作詳細資訊(如abstract或virtual)等。使用Type的GetConstructors或 GetConstructor方法來呼叫特定的建構子。
(4)使用MethodInfo來了解方法的名稱、回傳類型、參數、存取修飾符(如 pulic 或private)和實作詳細資訊(如abstract或virtual)等。使用Type的GetMethods或GetMethod方法來呼叫特定的 方法。
(5)使用FiedInfo了解欄位的名稱、存取修飾符(如public或private)和實作詳細資訊(如static)等,並取得 或設定欄位值。
(6)使用EventInfo了解事件的名稱、事件處理程序資料類型、自訂屬性、宣告類型和反射類型等,新增或移除事件處理程 序。
(7)使用PropertyInfo了解屬性的名稱、資料型態、宣告型別、反射型別及唯讀或可寫入狀態等,取得或設定屬性值。
(8)使用ParameterInfo來了解參數的名稱、資料型別、是輸入參數或輸出參數,以及參數在方法簽章中的位置等。
3、與反射相關的命名空間:
System.Reflection.Assembly
System.Reflection.MemberInfo
System.Reflection.Re.InfoSystem.Reflection.MemberInfo
System.Reflection.Re.id.S. ConstructorInfo
System.Reflection.MethodInfo
System.Reflection.PropertyInfo
System.Type
4、反射的層次模型:
: 1. 可以使用反射動態地建立類型的實例,將類型綁定到現有對象,或從現有對像中取得類型
2. 應用程式需要在執行時間從某個特定的程式集中載入一個特定的類型,以便在實現某個任務時可以用到反射。
3. 反射主要應用與類別庫,這些類別庫需要知道一個類型的定義,以便提供更多的功能。
應用要點:
1. 現實應用程式中很少有應用程式需要使用反射類型
2. 使用反射動態綁定需要犧牲效能
3. 有些元資料資訊是不能透過反射取得的
4. 某些反射類型是專門為那些CLR開發編譯器的開發使用的,所以你要意識到不是所有的反射類型都是適合每個人的。
6、反射的實際應用:
反射appDomain 的程序集
static void Main
{
// 透過GetAssemblies 呼叫appDomain的所有程序集
foreach (Assembly assem in Appdomain.currentDomain.GetAssemblies(Assembly assem in Appdomain.currentDomain.GetAssemblies(GetAssembly)> reflector.ReflectOnAssembly(assem)
}
}
說明:呼叫AppDomain 物件的GetAssemblies 方法將傳回由System.Reflection.Assembly元素組成的陣列。
反射單一組件
我們可以顯示的呼叫其中的一個組件,system.reflecton.assembly 類型提供了以下三種方法:
1. Load 方法:極力推薦的一種方法,Load 方法帶有一個組件標誌並載入它,Load 將引起CLR把策略應用到組件上,先後在全域組件緩衝區,應用程式基目錄和私有路徑下面查找該程序集,如果找不到該程序集系統拋出異常。
2. LoadFrom 方法:傳遞一個組件檔案的路徑名(包括副檔名),CLR會載入您指定的這個程式集,傳遞的這個參數不能包含任何關於版本號的信息,區域性,和公鑰訊息, 如果在指定路徑找不到組件拋出例外。
3. LoadWithPartialName:永遠不要使用這個方法,因為應用程式無法確定再在載入的組件的版本。此方法的唯一用途是幫助那些在.Net框 架的測試環節使用.net 框架提供的某種行為的客戶,這個方法將最終被拋棄不用。
注意:system.AppDomain 也提供了一種Load 方法,他和Assembly的靜態Load 方法不一樣,AppDomain的load 方法是一種實例方法,返回的是一個對程序集的引用,Assembly的靜態Load 方發將程式集按值封裝發回給發出呼叫的AppDomain.盡量避免使用AppDomain的load 方法
利用反射獲取類型資訊
一個簡單的利用反射獲取類型資訊的例子:
using system;
using sytem. reflection;
class reflecting
{
static void Main(string[]args)
{
reflecting reflect=new reflecting();// 定義一個新的自身類別
//呼叫一個reflecting.exe大約assembly.loadfrom(“reflecting.exe”)
reflect.getreflectioninfo(myAssembly);// 取得反射資訊
}
// 定義一個取得反射內容的方法
void getreflectioninfo(assembly mhyasse)> myassemby.Gettypes();//取得類型
foreach (type type in typearr)//針對每個類型取得詳細資訊
{
//取得類型的結構資訊
constructorinfo[] myconstructors=type.GetConstructors;
//取得類型的欄位資訊
fieldinfo[] myfields=type.GetFiedls()
//取得方法資訊
MethodInfo myMethodInfo=type.GetMethods();
// 取得屬性資訊
propertyInfo[] myproperties=type.Gpperties=type.取得事件資訊
EventInfo[] Myevents=type.GetEvents;
}
}
}
其它幾種取得type物件的方法:
1. System.type 參數為字串類型,該字串必須指定類型的完整名稱(包括其命名空間)
2. System.type 提供了兩個實例方法:GetNestedType,GetNestedTypes
3. Syetem.Reflection.Assembly 類型提供的實例方法為:GetType,GetTypes,GetExporedTypes
4. System.Reflection.Moudle 提供了這些實例方法:GetType,GetTypes,FindTypes
設定反射類型的成員
反射類型的成員就是反射層次模型中最下面的一層資料。我們可以透過type物件的 GetMembers 方法來取得一個類型的成員。如果我們使用的是不含參數的GetMembers,它只會傳回該類型的公共定義的靜態變數和實例成員,我們也可以透過使用帶有參數的 GetMembers透過參數設定來傳回指定的類型成員。特定參數參考msdn 中system.reflection.bindingflags 枚舉類型的詳細說明。
例如:
// 設定需要傳回的類型的成員內容
bindingFlags bf=bingdingFlags.DeclaredOnly|bingdingFlags.Nonpublic|BingdingFlags.Public;
foreach (MInfoInfomimi int temberm; mi.membertype) //輸出指定的類型成員
}
透過反射建立類型的實例
透過反射可以取得組件的類型,我們就可以根據所獲得的組件類型來建立該類型新的實例,這也是前面提到的在運行時創建物件實現晚綁定的功能。我們可以透過下面的幾個方法來實現:
1. System.Activator 的CreateInstance方法。該方法傳回新物件的引用。
2. System.Activator 的createInstanceFrom 與上一個方法類似,不過需要指定類型及其組件。
3. System.Appdomain 的方法:createInstance,CreateInstanceAndUnwrap,CreateInstranceFrom和 CreateInstraceFromAndUnwrap
4. System.type 的InvokeMember實例方法:這個方法傳回一個與傳入參數相符的建構函數,並且建構這個型別。
5. System.reflection.constructinfo 的Invoke實例方法
反射類型的介面
如果你想要取得一個類型繼承的所有介面集合,可以呼叫 Type的FindInterfaces GetInterface或 GetInterfaces。所有這些方法只能返回該類型直接繼承的接口,他們不會返回從一個接口繼承下來的接口。要返回介面的基礎介面必須再次呼叫上述方法。
反射的性能
反射時CLR要做更多的工作:校驗參數,檢查權限等等,速度是非常慢的。 盡量不要使用反射進行編程,對於打算編寫一個動態構造類型(晚綁定)的應用程序,可採取以下幾種方式進行代替:
1.透過類別的繼承關係。讓該類型從一個編譯時可知的基礎類型派生出來,在運行時產生該類型的一個實例,將對其的引用放到其基礎類型的一個變數中,然後調用該基礎類型的虛擬方法。
2.透過接口實現。在運行時,建構該類型的一個實例,將對其的引用放到其介面類型的變數中,然後呼叫該介面定義的虛擬方法。
3.透過委託實現。讓該類型實作一個方法,其名稱和原型都與一個在編譯時就已知的委託相符。在執行時先建構該類型的實例,然後在用該方法的物件及名稱建構出該委託的實例,接著透過委託呼叫你想要的方法。這個方法相對與前面兩個方法所做的工作要多一些,效率也更低一些。
使用注意事項:
1、跨程序集的反射
在開發中,經常會遇到這種情況,在A.dll中需要反射B.dll中的類型,如果稍不注意,就會產生運行時錯誤。關於跨程式集的反射,記住兩點:
(1)如果使用typeof,編譯能通過,則跨程式集的反射一定可以正常運作。可以說,typeof是支援強型別的。例如
Type supType = typeof(EnterpriseServerBase.DataAccess.IDBAccesser) ;
如果目前組件沒有新增對EnterpriseServerBase.dll的引用,則編譯會報錯。
(2)如果使用Type.GetType,情況就複雜些,這是因為Type.GetType是非強類型的。 Type.GetType的參數是一個 string,當string表示的目標類型不在目前程式集中,則執行時Type.GetType會傳回null。解決的方法是:先載入目標組件,然後再使用Assembly.GetType方法。如
Assembly asmb = Assembly.LoadFrom("EnterpriseServerBase.dll") ;
Type supType = asmb.GetType("EnterpriseServerBase.DataAccess.IDBAccesser") ;
注意,使用類型. EnterpriseServerBase.dll的引用,Type.GetType("EnterpriseServerBase.DataAccess.IDBAccesser")也會傳回null,這是因為Type.GetType只會在目前程式集中進行型別搜尋。
2、反射時判斷一個方法的回傳型別是否為void
Type serviceType = typeof(T);
MethodInfo methodInfo = serviceType.GetMethod(methodName);
即可。

C#和.NET適用於Web、桌面和移動開發。 1)在Web開發中,ASP.NETCore支持跨平台開發。 2)桌面開發使用WPF和WinForms,適用於不同需求。 3)移動開發通過Xamarin實現跨平台應用。

C#.NET生態系統提供了豐富的框架和庫,幫助開發者高效構建應用。 1.ASP.NETCore用於構建高性能Web應用,2.EntityFrameworkCore用於數據庫操作。通過理解這些工具的使用和最佳實踐,開發者可以提高應用的質量和性能。

如何將C#.NET應用部署到Azure或AWS?答案是使用AzureAppService和AWSElasticBeanstalk。 1.在Azure上,使用AzureAppService和AzurePipelines自動化部署。 2.在AWS上,使用AmazonElasticBeanstalk和AWSLambda實現部署和無服務器計算。

C#和.NET的結合為開發者提供了強大的編程環境。 1)C#支持多態性和異步編程,2).NET提供跨平台能力和並發處理機制,這使得它們在桌面、Web和移動應用開發中廣泛應用。

.NETFramework是一個軟件框架,C#是一種編程語言。 1..NETFramework提供庫和服務,支持桌面、Web和移動應用開發。 2.C#設計用於.NETFramework,支持現代編程功能。 3..NETFramework通過CLR管理代碼執行,C#代碼編譯成IL後由CLR運行。 4.使用.NETFramework可快速開發應用,C#提供如LINQ的高級功能。 5.常見錯誤包括類型轉換和異步編程死鎖,調試需用VisualStudio工具。

C#是一種由微軟開發的現代、面向對象的編程語言,.NET是微軟提供的開發框架。 C#結合了C 的性能和Java的簡潔性,適用於構建各種應用程序。 .NET框架支持多種語言,提供垃圾回收機制,簡化內存管理。

C#和.NET運行時緊密合作,賦予開發者高效、強大且跨平台的開發能力。 1)C#是一種類型安全且面向對象的編程語言,旨在與.NET框架無縫集成。 2).NET運行時管理C#代碼的執行,提供垃圾回收、類型安全等服務,確保高效和跨平台運行。

要開始C#.NET開發,你需要:1.了解C#的基礎知識和.NET框架的核心概念;2.掌握變量、數據類型、控制結構、函數和類的基本概念;3.學習C#的高級特性,如LINQ和異步編程;4.熟悉常見錯誤的調試技巧和性能優化方法。通過這些步驟,你可以逐步深入C#.NET的世界,並編寫高效的應用程序。


熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

Video Face Swap
使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱門文章

熱工具

WebStorm Mac版
好用的JavaScript開發工具

Dreamweaver CS6
視覺化網頁開發工具

SAP NetWeaver Server Adapter for Eclipse
將Eclipse與SAP NetWeaver應用伺服器整合。

EditPlus 中文破解版
體積小,語法高亮,不支援程式碼提示功能

Safe Exam Browser
Safe Exam Browser是一個安全的瀏覽器環境,安全地進行線上考試。該軟體將任何電腦變成一個安全的工作站。它控制對任何實用工具的訪問,並防止學生使用未經授權的資源。