如果您確實設置了所有屬性和字段,沒有比您已經編寫的代碼更好的方法。您可以編寫一個擴展方法並將其合併到System命名空間中,這樣它就會出現在任何類型的每個實例上;我也認真考慮使用StringBuilder
,AppendLine
和string.Format
:
namespace System
{
public static class MyExtensions
{
public static string Report<T>(this T instance)
{
StringBuilder sb = new StringBuilder();
foreach (PropertyInfo prop in typeof(T).GetProperties())
{
sb.AppendLine(
string.Format("{0} = {1}", prop.Name, prop.GetValue(si, null));
}
foreach (FieldInfo prop in typeof(T).GetFields())
{
sb.AppendLine(
string.Format("{0} = {1}", prop.Name, prop.GetValue(si, null));
}
return sb.ToString();
}
}
}
一旦你寫了這個,你可以簡單地做:
var instance = new ServerInfo();
var report = instance.Report();
這裏的問題是,它不處理情況下,類型的最佳表示形式實際上只是一個'ToString'調用 - 例如int
或string
(特別是字符串;因爲此代碼將僅輸出Length
成員)。
你提到WPF數據網格 - 這是值得一提的是,不直接使用反射,而是使用了System.ComponentModel.TypeDescriptor
類 - 這是可擴展的,並使用TypeConverter
機制,以支持從字符串(遠好於單純依靠轉換/ ToString
)。
但是,它不包含它生成的元數據中的字段;你明確想要的。
作爲最後一點,我會爭辯說,這種事情不應該在程序中使用很多;因爲這種細節水平很少很重要。那麼你的報告應該走多深的問題;對於每個成員,如果你實際上不再使用Report
(在這種情況下,你必須將通用後綴綁定,或者只是使用object
來代替)?但是,你有令人討厭的代碼來檢查應該下降的類型,或者只是ToString
'd。如果你開始這樣做,你還需要注意不要通過交叉引用遞歸;否則你的報告方法可能會鎖定你的應用程序。
我會建議,而不是一個接口是最好的:
public interface IReportable
{
void Report(StringBuilder target);
}
的接口,那麼只限於你真的需要報告的類型的實現;並且您可以使用上面的擴展方法或其他類似擴展方法作爲大多數類型的默認實現。然而,至關重要的是,如果需要的話,一種類型可以提供它自己的類型。
可用的代碼[here](http://stackoverflow.com/a/6745255/870604)非常簡單,爲什麼你不想使用它? – ken2k 2012-02-13 09:15:49
你在答案中不喜歡什麼? – 2012-02-13 09:16:18
用什麼東西代替? – 2012-02-13 09:20:30