随分前に追加されたrecord型を今更ながら使い始めました。
内部的にはクラスと同じ扱いで、プロパティは全て不変とは以前から知っていたのですが、
先日recordもstructと同様にIEquatableが実装されていると聞き、
それならDictionaryのキーなどでも使いやすく、
1行で定義を済ませられるのも楽で良いなと思い使ってみることにした次第です。
ひとまず、以下のようなrecordを定義してみました。
/// <summary> 汎用結果クラス </summary>
/// <param name="Succ"> 成功したか </param>
/// <param name="ErrMsg"> 失敗時のエラーメッセージ </param>
record Result(bool Succ, string ErrMsg = "");
/// <summary> 汎用結果クラス </summary>
/// <param name="Succ"> 成功したか </param>
/// <param name="Value"> 戻り値 </param>
/// <param name="ErrMsg"> 失敗時のエラーメッセージ </param>
record Result(bool Succ, T Value = default, string ErrMsg = "");
よくタプルで成否のbool値と成功時の戻り値、失敗時のエラーメッセージを書いていたのですが、
クラスにするほどでもないけれど一々書くには若干手間だったので、
手軽に定義・使用できて良かったです。
今のところ以下のような場合にrecordを使うのが良いのかなと思っています。
・不変にしたい
・辞書のキーとしてのみ使用する
・特にメソッドなど実装予定なし
どこで使うべきかは正直、手を動かして使ってみないことには見極められない気がしているので、
今後も機を見て使っていこうと思います。
また、業務プロジェクト(C#9.0, .Netframework4.6-4.8)でrecordを宣言すると、
次のようなエラーが出て使用できませんが、
「定義済みの型’System.Runtime.CompileServices.IsExternalInit’は定義またはインポートされていません。」
以下の記事の通り、IsExternalInitクラスを自前でinternalで定義するとエラー解消し、使用できました。
(記事タイトル通り、record型だけでなくinitアクセサも使用できるようになりました)
言語か.netのバージョンが不足しているのだと思い諦めかけたのですが、
調べてみたら解決して良かったです。
以上です。