私は全く読まなかったので最初に質問してください、ここに新しい答えがあります(これはちょっとしたことですので、最後までスキップしてリンクに従うことができます):
組み込みシリアライザクラスを取得することはできませんあなたが動作するために必要な属性を追加したくないからです。あなたの唯一の選択肢は、自分自身でクラスをセロライズすることですが、これは聞こえるほど退屈である必要はありません。数年前に仮想モードのDataGridViewで同様の問題が発生し、表示用にデータを仮想化するために使用できる汎用バーチャライザーが作成されました。
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false)]
public sealed class showColumnAttribute : System.Attribute
{
///<summary>Optional display format for column</summary>
public string Format;
///<summary>Optional Header string for column<para>Defaults to propety name</para></summary>
public string Title;
///<summary>Optional column edit flag - defaults to false</summary>
public bool ReadOnly;
///<summary>Optional column width</summary>
public int Width;
///<summary>
///Marks public properties that are to be displayed in columns
///</summary>
public showColumnAttribute()
{
Format = String.Empty;
Title = String.Empty;
ReadOnly = false;
Width = 0;
}
}
そしてコンストラクタ:
///<summary>
///Extracts the properties of the supplied type that are to be displayed
///<para>The type must be a class or an InvalidOperationException will be thrown</para>
///</summary>
public Virtualiser(Type t)
{
if (!t.IsClass)
throw new InvalidOperationException("Supplied type is not a class");
List<VirtualColumnInfo> definedColumns = new List<VirtualColumnInfo>();
PropertyInfo[] ps = t.GetProperties();
MethodInfo mg, ms;
for (int i = 0; i < ps.Length; i++)
{
Object[] attr = ps[i].GetCustomAttributes(true);
if (attr.Length > 0)
{
foreach (var a in attr)
{
showColumnAttribute ca = a as showColumnAttribute;
if (ca != null)
{
mg = ps[i].GetGetMethod();
if (mg != null)
{
ms = ps[i].GetSetMethod();
definedColumns.Add
(
new VirtualColumnInfo
(
ps[i].Name, ca.Width, ca.ReadOnly, ca.Title == String.Empty ? ps[i].Name : ca.Title,
ca.Format, mg, ms
)
);
}
break;
}
}
}
}
if (definedColumns.Count > 0)
columns = definedColumns.ToArray();
}
これは、クラスのパブリックプロパティを抽出し、消耗品は、ヘッダー、フォーマットなどと一緒に列としてのDataGridViewにアイテムをマークし、それは、カスタム属性を使用しました
このすべて(および欠けているコードの残りの部分)の効果は、パブリックプロパティにタグを付けるだけで、特定のタイプの仮想化ツールを呼び出すことで、どのタイプもデータグリッドビューで仮想化できるということでした。
#region Virtualisation
static readonly Virtualiser Virtual = new Virtualiser(typeof(UserRecord));
[XmlIgnore] // just in case!
public static int ColumnCount { get { return Virtual.ColumnCount; } }
public static VirtualColumnInfo ColumnInfo(int column)
{
return Virtual.ColumnInfo(column);
}
public Object GetItem(int column)
{
return Virtual.GetItem(column, this);
}
/*
** The supplied item should be a string - it is up to this method to supply a valid value to the property
** setter (this is the simplest place to determine what this is and how it can be derived from a string).
*/
public void SetItem(int column, Object item)
{
String v = item as String;
int t = 0;
if (v == null)
return;
switch (Virtual.GetColumnPropertyName(column))
{
case "DisplayNumber":
if (!int.TryParse(v, out t))
t = 0;
item = t;
break;
}
try
{
Virtual.SetItem(column, this, item);
}
catch { }
}
#endregion
列の数、それらの特性及び順序は、クラスデータに由来するパブリックプロパティの数を作成することによって自動的に指定することができる。
#region Display columns
[showColumn(ReadOnly = true, Width = 100, Title = "Identification")]
public String DisplayIdent
{
get
{
return ident;
}
set
{
ident = value;
}
}
[showColumn(Width = 70, Title = "Number on Roll")]
public int DisplayNumber
{
get
{
return number;
}
set
{
number = value;
}
}
[showColumn(Width = -100, Title = "Name")]
public string DisplayName
{
get
{
return name == String.Empty ? "??" : name;
}
set
{
name = value;
}
}
#endregion
これは、表示するためのDataGridViewおよび編集するための任意のクラスを仮想化することになりますデータと私は何年も何度もそれを使用し、表示するプロパティの抽出はまさにXMLのシリアル化に必要なものであり、実際には、多くの同じ特性を持っています。
私はこのメソッドをXMLシリアル化のために同じ仕事をするように改造しようとしていましたが、すでに誰かがhttps://www.codeproject.com/script/Articles/ViewDownloads.aspx?aid=474453でそれを行っています。この方法を使って問題を解決できることを願っています。
1、サブクラス2はサブクラス1から拡張されます 2、はい私は、エンティティクラスの型を定義することで配列アイテムを定義できます(私は質問に入れました)ことは、私はサブクラス'エンティティ'クラスですべてを定義する必要はありません。属性やタイプなどに基づいて自動的にそれを行うようにしたい –
残念ながら、出力はレコードの内容を除いて同じです: Test1 20/09/2017 SubClass1Item> < SubClass2Item> Test2 20/09/2017 01:25:34 SubClass2Item> –
あなたは依然として配列項目と型名をエンティティクラスに定義しています。それは私が望まないものです。私はそれがすでに元のコメントになっています。私はそのようなサブクラス自体で定義する方法をしたい –