【C#】エンティティクラスから一部のプロパティのみをCSV出力したい(カスタム属性使用)
エンティティクラスのプロパティにカスタム属性を付けて、その属性を基にCSVへ出力をします。
また、カスタム属性には、出力順とヘッダーテキストを設定できるようにします。
①カスタム属性クラスをつくります。
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
[AttributeUsage(AttributeTargets.Property, AllowMultiple = false, Inherited = false)] | |
public class CSVExportAttribute : Attribute | |
{ | |
/// <summary> | |
/// CSVへの出力順です。 | |
/// </summary> | |
public int OutputID { get; private set; } | |
/// <summary> | |
/// カラムのヘッダーテキストです。 | |
/// </summary> | |
public string ColumnsHeaderText { get; private set; } | |
/// <summary> | |
/// コンストラクタ | |
/// </summary> | |
/// <param name="outputID">CSVへの出力順を指定してください。</param> | |
/// <param name="columnHeaderText">カラムのヘッダーテキストを指定してください。</param> | |
public CSVExportAttribute(int outputID, string columnHeaderText) | |
{ | |
OutputID = outputID; | |
ColumnsHeaderText = columnHeaderText; | |
} | |
} |
今回のカスタム属性はプロパティ向けなので、ターゲットをAttributeTargets.Propertyに。
多重設定を許さないので、AllowMultiple = falseに。
継承は必要ないので、Inherited = falseに。
②エンティティクラス(適当)を用意して、出力したいプロパティにカスタム属性を設定します。
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
public class SourceEntity | |
{ | |
[CSVExport(1, "管理番号")] | |
public int SourceID { get; set; } | |
public DateTime RegistDate { get; set; } | |
[CSVExport(2,"苗字")] | |
public string FirstName { get; set; } = string.Empty; | |
[CSVExport(3,"名前")] | |
public string LastName { get; set; } = string.Empty; | |
public int Age { get; set; } | |
[CSVExport(5,"数学の偏差値")] | |
public int MathematicalDeviationValue { get; set; } | |
[CSVExport(6,"科学の偏差値")] | |
public int ScienceDeviationValue { get; set; } | |
[CSVExport(8,"英語の偏差値")] | |
public int EnglishDeviationValue { get; set; } | |
[CSVExport(4,"国語の偏差値")] | |
public int JapaneseDeviationValue { get; set; } | |
[CSVExport(7,"社会の偏差値")] | |
public int SocialDeviationValue { get; set; } | |
} |
※超適当でごめんなさい。
③動作確認のため、エンティティクラスに適当に値を設定します。
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// 動作確認用のエンティティを作成します。 | |
var entities = new List<SourceEntity>() | |
{ | |
{ new SourceEntity{ SourceID=1, RegistDate=DateTime.Now, Age=16, FirstName="ichiro", LastName="yamada", | |
EnglishDeviationValue=50, JapaneseDeviationValue=50, MathematicalDeviationValue=50, ScienceDeviationValue=50, SocialDeviationValue=50} }, | |
{ new SourceEntity{ SourceID=2, RegistDate=DateTime.Now, Age=15, FirstName="jiro", LastName="suzuki", | |
EnglishDeviationValue=60, JapaneseDeviationValue=45, MathematicalDeviationValue=55, ScienceDeviationValue=55, SocialDeviationValue=40} }, | |
{ new SourceEntity{ SourceID=3, RegistDate=DateTime.Now, Age=16, FirstName="saburo", LastName="honda", | |
EnglishDeviationValue=45, JapaneseDeviationValue=40, MathematicalDeviationValue=60, ScienceDeviationValue=60, SocialDeviationValue=40} }, | |
{ new SourceEntity{ SourceID=4, RegistDate=DateTime.Now, Age=17, FirstName="shiro", LastName="matsuda", | |
EnglishDeviationValue=65, JapaneseDeviationValue=65, MathematicalDeviationValue=60, ScienceDeviationValue=65, SocialDeviationValue=65} }, | |
{ new SourceEntity{ SourceID=5, RegistDate=DateTime.Now, Age=14, FirstName="goro", LastName="toyoda", | |
EnglishDeviationValue=40, JapaneseDeviationValue=45, MathematicalDeviationValue=45, ScienceDeviationValue=40, SocialDeviationValue=40} } | |
}; |
※ここからは、エンティティクラスを使用する任意のクラス、処理内に記載しています。
④カスタム属性が設定されたプロパティのみを抽出して、出力順を昇順に並び替えます。
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// CSVExportAttributeが設定されたプロパティを取得します。 | |
var exportProperties = typeof(SourceEntity).GetProperties().Where(e => Attribute.IsDefined(e, typeof(CSVExportAttribute))).ToList(); | |
// 出力するプロパティが無ければ処理終了します。 | |
if (exportProperties == null || exportProperties.Count == 0) | |
return false; | |
// OutputIDの値で並び替えます。 | |
exportProperties = exportProperties.OrderBy(e => ((CSVExportAttribute)Attribute.GetCustomAttribute(e, typeof(CSVExportAttribute))).OutputID).ToList(); |
もう少しスマートなLinqの使い方が… .Where(...).OrderBy(...).Select(...)で書けばよいと思うの。
⑤カスタム属性のヘッダーテキストと出力データを抽出します。
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// ヘッダーテキストを取得します。 | |
var headerTextList = exportProperties.Select(e => ((CSVExportAttribute)Attribute.GetCustomAttribute(e, typeof(CSVExportAttribute))).ColumnsHeaderText).ToList(); | |
// 出力対象の実データを取得します。 | |
var exportVales = new List<List<string>>(); | |
foreach(var entity in entities) | |
{ | |
var element = exportProperties.Select(e => typeof(SourceEntity).GetProperty(e.Name).GetValue(entity).ToString()).ToList(); | |
exportVales.Add(element); | |
} |
※ここでは、エンティティの各プロパティもList<string>として格納していますが、お好きな様にしてください。
⑥取り出した値をカンマ区切りでテキストファイルに出力します。
ソースは特別載せませんが、今回はList<List<string>>で渡していますので、1レコードの文字列リストをカンマでつないで1行として出力をしています。
※参考:出力結果
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
管理番号,苗字,名前,国語の偏差値,数学の偏差値,科学の偏差値,社会の偏差値,英語の偏差値 | |
1,ichiro,yamada,50,50,50,50,50 | |
2,jiro,suzuki,45,55,55,40,60 | |
3,saburo,honda,40,60,60,40,45 | |
4,shiro,matsuda,65,60,65,65,65 | |
5,goro,toyoda,45,45,40,40,40 |
※動作確認はVS2022(preview)/.Net6(preview)です。
コメント
コメントを投稿