本文へスキップ
BecomeCoder

C#文法コース · 第4章 メソッド · レッスン36

拡張メソッド

ブラウザで完結

導入

"hello".ToUpper()のように、型が最初から持っているメソッドは便利です。ではstringintなど自分では変更できない既存の型に、あたかも元から持っていたかのようにメソッドを足せたら——それを実現するのが拡張メソッドです。次章のLINQ(WhereSelectなど)も、実はコレクションに対する拡張メソッドの集まりです。

図解

flowchart LR
    S["string 型(変更できない)"] --> E["拡張メソッド Shout()"]
    E --> U["&quot;world&quot;.Shout()<br/>と書けるようになる"]
    U --> R["&quot;WORLD!&quot;"]

サンプル

string name = "world";
Console.WriteLine(name.Shout());       // WORLD! ← 元からあるメソッドのように呼べる
Console.WriteLine("abc".Repeat(3));    // abcabcabc

// 拡張メソッドは「static クラスの static メソッド」で、
// 第1引数に this を付ける。その this の型に生えたように見える
static class StringExtensions
{
    public static string Shout(this string s) => s.ToUpper() + "!";
    public static string Repeat(this string s, int count)
        => string.Concat(Enumerable.Repeat(s, count));
}
  • 拡張メソッドは**staticクラスstaticメソッド**として定義する
  • 第1引数にthis 型 名前を付けると、その型のメソッドのように値.メソッド()で呼べる
  • 既存の型(stringint・自作クラス・コレクション)に手を加えずに機能を足せる
  • LINQの正体Where/SelectなどはIEnumerable<T>に対する拡張メソッド

演習

int n = 4;

// TODO: int の拡張メソッド IsEven()(偶数なら true を返す)を定義し、
//       n.IsEven() の結果を出力してください(True)
Console.WriteLine(n.IsEven());

static class IntExtensions
{
    ___
}
  • 期待される出力: True
ヒント1を見る

public static bool IsEven(this int x) => x % 2 == 0;

ヒント2を見る

IntExtensionsの中に上のメソッドを1つ書くだけです

まとめ

  • 拡張メソッドは既存の型に、変更せずメソッドを後付けできる
  • staticクラスのstaticメソッドで、第1引数にthisを付ける
  • LINQのメソッド群も拡張メソッドとして提供されている

次章: データ操作を宣言的に書ける「LINQ」へ進みます。

実際に動かしてみよう

本文のサンプルや演習のコードは、コードブロック右上の「コピー」ボタンでコピーして、下のエディタに貼り付ければそのまま実行できます。

C# — ブラウザ内で実行

ブラウザ内でC#を動かす環境を読み込みます(初回のみ数秒)。
スクロールして表示された時点でも自動で読み込まれます。