かずきのBlog@hatena

日本マイクロソフトに勤めています。XAML + C#の組み合わせをメインに、たまにASP.NETやJavaなどの.NET系以外のことも書いています。掲載内容は個人の見解であり、所属する企業を代表するものではありません。

partialクラス

部分型定義(その4)←らへんで話題になってるpartialクラス。
ちょっくら簡単に復習。


とりあえずこんな風に、クラスの定義をばらして書くことが出来るが出来る。

using System;
using System.Collections.Generic;
using System.Text;

namespace PartialSample
{
    /// <summary>
    /// Sampleクラスだ!
    /// </summary>
    partial class Sample
    {
        public void Foo()
        {
            Console.WriteLine("Foo");
        }
    }

    /// <summary>
    /// こっちにもSampleクラスだ!
    /// </summary>
    partial class Sample
    {
        public void Boo()
        {
            Console.WriteLine("Boo");
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            // FooもBooもつかえる
            Sample s = new Sample();
            s.Foo();
            s.Boo();
        }
    }

}

これは、基本なので問題なし。
ということで、ちょっと請った事するとぶちあたりそうなこと。

Generic

Genericを使ったクラスだと…

using System;
using System.Collections.Generic;
using System.Text;

namespace PartialSample
{
    /// <summary>
    /// Sampleクラスだ!
    /// </summary>
    partial class Sample<T>
    {
        public void Foo(T t)
        {
            Console.WriteLine(t);
        }
    }

    /// <summary>
    /// こっちにもSampleクラスだ!
    /// </summary>
    partial class Sample<T>
    {
        public void Boo(T u)
        {
            Console.WriteLine(u);
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            // FooもBooもつかえる
            Sample<string> s = new Sample<string>();
            s.Foo("a");
            s.Boo("b");
        }
    }

}

こんな具合になる。

これが

partial class Sample<T> ....

partial class Sample<U> .... // 名前違う!?

だとコンパイルエラーになる。
同じ名前で同じ順序でGenericの引数を指定しないといけない。

継承

Genericは同じパラメータを同じようにつけないといけない。
継承は…?

using System;
using System.Collections.Generic;
using System.Text;
using System.ComponentModel;

namespace PartialSample
{
    /// <summary>
    /// こっちはComponent
    /// </summary>
    partial class Sample<T> : Component
    {
        public void Foo(T t)
        {
            Console.WriteLine(t);
        }
    }

    /// <summary>
    /// こっちはIComparable
    /// </summary>
    partial class Sample<T> : IComparable
    {
        public void Boo(T u)
        {
            Console.WriteLine(u);
        }

        #region IComparable メンバ

        public int CompareTo(object obj)
        {
            EventHandlerList l = this.Events; // Componentのメンバにアクセス出来る
            return 0;
        }

        #endregion
    }

    class Program
    {
        static void Main(string[] args)
        {
            // FooもBooもつ変える
            Sample<string> s = new Sample<string>();
            s.Foo("a");
            s.Boo("b");
            s.CompareTo(new Sample<string>()); // Comparableのメンバもちゃんと呼べる
        }
    }

}

かなり柔軟にやってくれる。

下のほうのSampleでComponentの継承を付け足してもOK。
同じならいいんだって。

もちろん同じpartialクラスで違うクラスを継承するように書くとコンパイルエラー。