ずっとわかんなかったことに取り組んだ。古いc#でmap/filter

新しいC#だとmap/filter使えるんですかね?知りません。C#2.0で実験。

http://d.hatena.ne.jp/yuki_neko_nyan/20070116/1168928753
がずっとわかりませんでした。

えーっと、、これってGoFのVisitorパターンじゃないの?そうかそうか、Visitorってlambdaのことだったんだね!

その納得はずっとshareできませんでしたよ。
今日何となくわかった気がするのでC#に移植して実験

//インターフェース
using System;

public interface Mappable
{
    MapFilterAbledList map(Maplambda target);
}
public interface FIleterable
{
    MapFilterAbledList filter(FIleterlambda target);
}
public interface Maplambda
{
   Object eval(Object target);
}
public interface FIleterlambda
{
   bool eval(Object target);
}
//mapとfilterが使えるArrayListクラス
using System;
using System.Collections;

public class MapFilterAbledList : ArrayList, Mappable, FIleterable
{
    /**************************************************************
      コンストラクタなどはArrayListクラスのものを流用するので未定義でOK
    ***************************************************************/

    public MapFilterAbledList map(Maplambda lambda)
    {
        MapFilterAbledList retList = new MapFilterAbledList();
        foreach (Object elem in this)
        {
            retList.Add(lambda.eval(elem));
        }
        return retList;
    }

    public MapFilterAbledList filter(FIleterlambda lambda)
    {
        MapFilterAbledList retList = new MapFilterAbledList();
        foreach (Object elm in this)
        {
            if (lambda.eval(elm))
                retList.Add(elm);
        }
        return retList;
    }
}
//main
using System;

class Program
{
    static void Main(string[] args)
    {
        MapFilterAbledList _t = new MapFilterAbledList();
        _t.Add(new Cat("1c", 1));
        _t.Add(new Cat("2c", 2));
        _t.Add(new Cat("3c", 3));
        _t.Add(new Cat("4c", 4));
        _t.Add(new Cat("5c", 5));
        _t.Add(new Cat("6c", 6));
        _t.Add(new Cat("7c", 7));

        //map
        MapFilterAbledList _t2 = _t.map(new mapTest_nameMap());
        //map済みを出力            
        foreach (String _s in _t2)
            Console.WriteLine(_s);
        //filter
        MapFilterAbledList _f = _t.filter(new filterTest_filter4(3));
        //filter済みを出力
        foreach (Cat c in _f)
            Console.WriteLine(c.Age);

        while (true) { }

    }
    //実験用クラス
    class Cat
    {
        public String name;
        public int Age;
        public Cat(string n, int a)
        {
            this.name = n; this.Age = a;
        }
    }
    //だってcat専用なんだもの
    class mapTest_nameMap : Maplambda
    {
        public Object eval(Object cat_)
        {
            return ((Cat)(cat_)).name;
        }
    }
    //だってcat専用なんだもの
    class filterTest_filter4 : FIleterlambda
    {
        public int sikii = 4;
        public filterTest_filter4(int s) { this.sikii = s; }
        public bool eval(Object cat_)
        {
            if (((Cat)cat_).Age > this.sikii)
                return true;
            else
                return false;
        }
    }
}

たしかにvisitorだわ、と思えた今日。ちょっとうれしい。
「じょうずにやけましたー」
やっとだよー。
いや、全然使いこなさないだろうけど。。。
ジェネリクス版とかつくりたいですよね。。。