Effective JavaのアレをC#で
ねた元はこちら:
なんぞこれ。コンストラクタパラメータが異常に大杉る・・・。バカなの?死ぬの?そういう場合はBuilderパターンを検討してみよう。 - Bug Catharsis
C#3.0とC#4.0の2つを考えてみました。
まず、ネタ元の本文に
このEffective JavaでJoshua Bloch氏が提案しているBuilderパターンは、
http://d.hatena.ne.jp/zecl/20091117/p1
Pythonに見られる名前付きオプションパラメータを模倣してJavaで実装したたもので、
「実装したたもので、」という部分がJavaのソースコードの冗長さをも表現しているのだと信じて止みませんが、脱線しましたが、話を戻しますが、えーっと、ということですので、1つめはC#4.0で加わったオプショナル引数をそのまま使っています。*1
2つめは、オプショナル引数が加わる前の、C#3.0での場合を考えてみました。コンストラクタ呼び出し時にプロパティを初期化できる、という点を利用しました。
以下がソースになります。何でもかんでも長いJavaよりは多少スッキリしたのではないでしょうか。
class Program { static void Main( string[] args ) { // C# 4.0 var foo = new VeryNiceClass( 10, 20, optional2 : 30 ); Console.WriteLine( foo ); // C# 3.0 var bar = new HyperUltraClass.Builder( 256, 512 ) { Optional1 = 1024, Optional3 = 2048 }.Build(); Console.WriteLine( bar ); } } // C# 4.0 ~ public class VeryNiceClass { private readonly int necessary1, necessary2; private readonly int? optional1, optional2, optional3; public VeryNiceClass( int necessary1, int necessary2, int? optional1 = null, int? optional2 = null, int? optional3 = null ) { this.necessary1 = necessary1; this.necessary2 = necessary2; this.optional1 = optional1; this.optional2 = optional2; this.optional3 = optional3; } public override string ToString() { return this.necessary1 + ":" + this.necessary2 + ":" + (this.optional1??0) + ":" + (this.optional2??0) + ":" + (this.optional3??0); } } // C# 3.0 ~ public class HyperUltraClass { private readonly int necessary1, necessary2; private readonly int? optional1, optional2, optional3; public class Builder { private int necessary1, necessary2; public int? Optional1 { get; set; } public int? Optional2 { get; set; } public int? Optional3 { get; set; } public Builder( int necessary1, int necessary2 ) { this.necessary1 = necessary1; this.necessary2 = necessary2; } public HyperUltraClass Build() { return new HyperUltraClass( necessary1, necessary2, this.Optional1, this.Optional2, this.Optional3 ); } } private HyperUltraClass( int necessary1, int necessary2, int? optional1, int? optional2, int? optional3 ) { this.necessary1 = necessary1; this.necessary2 = necessary2; this.optional1 = optional1; this.optional2 = optional2; this.optional3 = optional3; } public override string ToString() { return this.necessary1 + ":" + this.necessary2 + ":" + (this.optional1??0) + ":" + (this.optional2??0) + ":" + (this.optional3??0); } }
すごい久しぶりにC#触りました・・・。
やっぱりF#に比べてインテリセンスきもちい・・・。