今度は、比較演算子をオーバーライドします。
まず、どんなことがやりたいかというと、
1 2 3 4 | < members > < person name = 'masuda' >masuda tomoaki</ person > < person name = 'yamada' >yamada taro</ person > </ members > |
こんな風な XML があったときに、name 属性が “yamada” の要素をとりたいとします。
この場合のコードを
1 | EXElement el = doc / "members" / "person" % "name" == "yamada" ; |
と書きたい訳ですね。LINQ の文法で言えば、where 句があって、ってことになるのですが、そんな面倒なことを EXDoc ではやりませんッ!!! と言いますか、このあたりがコード上のシンタックスシュガーな訳なのです。
% 演算子を使って属性の値が取れるので、これを == 演算子で比較します。
普通は、bool 値で true/false で返すのですが、それでは意味がないのですね。どうせならば、マッチする要素を取って来てほしい。
なので、== 演算子の戻り値を、bool 型じゃなくて、EXElements 型にしてしまいますw
なんか、後で破綻しそうな気もしますが、別に構いません。C# の文法に則ったまま、ちょっと不思議な言語を作っている気分なので。
そんな訳で、== 演算子を多重定義します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 | public static EXElements operator ==(EXAttrs ats, string val) { EXElements items = new EXElements(); foreach (EXAttr at in ats) { if (at.Value == val) { items.Add(at._exElement); } } return items; } public static EXElements operator !=(EXAttrs ats, string val) { EXElements items = new EXElements(); foreach (EXAttr at in ats) { if (at.Value != val) { items.Add(at._exElement); } } return items; } public override bool Equals( object obj) { return base .Equals(obj); } public override int GetHashCode() { return base .GetHashCode(); } |
どうやら、== 演算子を多重定義すると自動的に、
・!= 演算子
・Equals メソッド
・GetHashCode メソッド
もオーバーライドする必要があるので、適当に入れておきます。
こうすることで、
1 | EXElement el = doc / "members" / "person" % "name" == "yamada" ; |
このコードが、思った通りに動くようになります。
そう、これって UIDD(User Interface Driven Development)と言ってもいいかもとか、思いました。あるいは、You & I Driven Development とか。
一応 wikipedia にもあるみたい。ちょっと違いますが。
http://ja.wikipedia.org/wiki/UIDD