設定檔+反射確實去除了選擇語句的繁瑣,帶來了優美的趕腳!
首先改進了一下類(接上文):
namespace ClassLib{ /// <summary> /// Interface IGreetingStrategy /// </summary> /// <remarks>Editor:v-liuhch CreateTime:2015/6/28 11:01:58</remarks> public interface IGreetingStrategy { string GreetingType { get; } void SetGreetingWords(ITextControl textContrl); } /// <summary> /// Class EnglishGreeting /// </summary> /// <remarks>Editor:v-liuhch CreateTime:2015/6/28 11:02:38</remarks> public class EnglishGreeting : IGreetingStrategy { public string GreetingType { get { return "English"; } } public void SetGreetingWords(ITextControl textContrl) { textContrl.Text = "hello,readers"; } } /// <summary> /// Class ChineseGreeting /// </summary> /// <remarks>Editor:v-liuhch CreateTime:2015/6/28 11:02:56</remarks> public class ChineseGreeting : IGreetingStrategy { private string greetingType; public ChineseGreeting(string greetingType) { this.greetingType = greetingType; } public ChineseGreeting() : this("中文") { } public ChineseGreeting(XmlNode section) { XmlAttribute attr = section.SelectSingleNode("params").Attributes["greetingType"];//擷取屬性值 greetingType = attr.Value;//為欄位賦值 } public string GreetingType { get { return greetingType; } } public void SetGreetingWords(ITextControl textContrl) { textContrl.Text = "你好啊,小讀者!"; } } /// <summary> /// Class GeneralClass:這個類可能還有很多的欄位,屬性,方法,這裡只是簡寫下 /// PS:GeneralClass是一個普通的類型,這個類內部維護著IGreetingStrategy,調用的時候還是根據多態具體調用。 /// </summary> /// <remarks>Editor:v-liuhch CreateTime:2015/6/28 11:08:04</remarks> public class GeneralClass { private IGreetingStrategy gs; public GeneralClass(IGreetingStrategy gs) { this.gs = gs; } public string GeneralProperty { get { //做一些額外的工作,這裡省略 return "<span sytle='color:red'>" + gs.GreetingType + "</span>"; } } public void GeneralMethod(ITextControl textContrl) { //做一些額外的工作,這裡省略 gs.SetGreetingWords(textContrl); textContrl.Text = "<span sytle='color:red'>" + textContrl.Text + "</span>"; //省略。。。。。。。 } }}
然後在設定檔中定義好我們要使用的具體類和自訂標籤的處理常式:
<!--greetingStrategy節點及其處理常式配置--> <configSections> <section name="greetingStrategy" type="ClassLib.GreetingConfigurationHandler,ClassLib"/> </configSections> <greetingStrategy type="ClassLib.ChineseGreeting,ClassLib"> <params greetingType="***中文問候***"/> <!--建構函式的參數--> </greetingStrategy>
這裡,ChineseGreeting是我們要使用的類,上面定義的是處理greetingStrategy的類;
接著,寫這個類的具體實現:
namespace ClassLib{ public class GreetingConfigurationHandler : IConfigurationSectionHandler { /* 處理有參數的建構函式的對象的建立: */ /// <summary> /// 建立配置節處理常式。 /// </summary> /// <param name="parent">父物件。</param> /// <param name="configContext">配置內容物件。</param> /// <param name="section">節 XML 節點。</param> /// <returns>建立的節處理常式對象。</returns> /// <exception cref="System.NotImplementedException"></exception> /// <remarks>Editor:v-liuhch CreateTime:2015/6/30 20:34:54</remarks> public object Create(object parent, object configContext, System.Xml.XmlNode section) { //擷取節點type屬性的值 Type t = Type.GetType(section.Attributes["type"].Value); object obj=null; try { /* 2,在要執行個體的類中加入一個建構函式,接收一個XmlNode節點,將greeting_stragetgy的節點在此傳遞,然後在這個建構函式中進行處理;*/ //如果t包含有參數為xmlnode的建構函式,直接使用這個建構函式 Type[] paras = { typeof(XmlNode) }; ConstructorInfo constructors = t.GetConstructor(paras); if (constructors != null) { object[] paramters = { section }; return Activator.CreateInstance(t, paramters); //傳入讀取到的建構函式的參數 } if (section.SelectSingleNode("params") == null) //無參數建構函式 { obj = Activator.CreateInstance(t); } else //有參數建構函式 { /*1,在此類中對策略類進行處理,取得params節點的屬性值,然後傳遞給具體執行個體化的類;*/ //擷取params節點的屬性greetingType的值 XmlAttribute attr = section.SelectSingleNode("params").Attributes["greetingType"]; object[] parameters = { attr.Value }; obj = Activator.CreateInstance(t, parameters); //傳入讀取到的建構函式的參數 } } catch (Exception) { return null; } return obj ; } }}
在建立方法中,我們先判斷ChineseGreeting類有沒有一個參數為節點的構造方法,如果有的話,就直接將section當作參數,在利用反射建立類型執行個體的時候傳進去;
如果沒有這樣的構造方法,我們就在這個處理類裡面讀取XML檔案中的參數,然後在類型執行個體化的時候傳進去;
兩種方式比較,其實都是一樣的,只過是這個參數讀取的早晚的問題;個人對比了下,覺得在這個類裡面讀取設定檔中的建構函式參數的方式更加靈活,個人偏愛。
寫個東西測試下:
#region 自訂節點儲存類型資訊——反射方法 IGreetingStrategy greetingStrategy = (IGreetingStrategy)ConfigurationManager.GetSection("greetingStrategy"); if (greetingStrategy != null) { GeneralClass generalClass = new GeneralClass(greetingStrategy); ltrGreetingType.Text = generalClass.GeneralProperty; generalClass.GeneralMethod(ltrGreetingWord); } #endregion
嘿嘿,相對方便。
感覺反射強大在把變化抽出來,但是抽出來的這個變化放到哪裡去最容易改動或者是後期維護成本較低,於是設定檔這時候就該上了。。。。。。
以上就是.Net設定檔——反射+設定檔儲存類型執行個體的內容,更多相關內容請關注topic.alibabacloud.com(www.php.cn)!