オブジェクトを他のオブジェクトにキャストして代入する時には、オブジェクトの型を変換する必要がでてきます。
C#には、オブジェクトの型を比較する演算子と、オブジェクトを別の型に変換するための演算子が用意されています。
今回の記事は、C#に用意されている比較演算子(型テスト演算子)の「is演算子」と変換演算子(型キャスト演算子)の「as演算子」について記載します。
目次
is演算子
is演算子とは
is演算子は2つのオブジェクトを比較し、変換可能であるかどうかを取得する型テスト演算子です。
「a is B」でaがB型に代入可能かどうか(aがBであるかどうか)をbool型の論理値(True/False)で返します。
is演算子では式(変数などのインスタンス)と、指定された型(クラスなどの定義)の間に互換性があるかどうかが調べられます。
is演算子の型テストを使用する式の形式(構文)は次のとおりです
1 2 |
// expressionがType型に変換(代入)できるか bool result = expression is Type; |
as演算子
as演算子とは
as演算子はオブジェクトを別の型のオブジェクトに変換するキャスト演算子です。
「a as B」でaをB型に変換したオブジェクト(Bとしてのaオブジェクト)を返します。
as演算子のキャストを使用する式の形式(構文)は次のとおりです
1 2 |
// expressionをType型に変換して変数に代入 var variable = expression as Type; |
キャスト演算子の()でキャストを行った場合、型変換ができない場合に例外が発生しますが、as演算子でキャストを行った場合は例外が発生せず、変数にnullが代入されます。
is演算子のパターンマッチング
C#7.0以降のis演算子では、パターンマッチングがサポートされており、パターンに対する式の結果のテストも行われます。
パターンマッチングを使用する型テスト
パターンマッチングには「型パターン」「定数パターン」「varパターン」の3種類があります。
型パターン
型パターンを使用してパターンマッチングを実行すると、式を指定された型に変換できるかどうかが、is演算子によってテストされます。
テストの結果、変換できる場合はその型の変数にキャストされます。
型パターンは次の形式(構文)で利用できます。
1 2 |
// パターンマッチングの構文 expression is Type variable |
定数パターン
定数パターンを使用してパターンマッチングを実行すると、式が指定された定数と等しいかどうかが、is演算子によってテストされます。
定数パターンは次の形式(構文)で利用できます。
1 2 |
// パターンマッチングの構文 expression is constant |
定数パターンを使用して、nullのチェックを行うこともできます。
1 2 |
// nullチェックを行う expression is null |
varパターン
varパターンは、すべての型または値に対応します。
is演算子の左辺の式(変数)は、コンパイル時の型と同じ型のローカル変数に割り当てられます。
is演算子の式の結果は常にTrueを返します。
varパターンは次の形式(構文)で利用できます。
1 2 |
// パターンマッチングの構文 expression is var variable |
varパターンではexpressionがnullの場合に、is演算子がTrueを返します。
型パターンでは指定された型に変換可能であっても、expressionがnullの場合には、is演算子はFalseを返します。
1 2 3 4 5 6 7 8 9 10 11 |
// Baseオブジェクトをnullで初期化 Base b = null; // 型パターン bool result1 = b is Base b1; // varパターン bool result2 = b is var b2; Console.WriteLine(result1); // False Console.WriteLine(result2); // True |
is演算子のパターンマッチングを使うと、as演算子を使わずにオブジェクトの変数へキャストした値を代入することができます。
1 2 3 4 5 6 7 8 9 10 11 12 |
// is演算子とas演算子 if (expression is SomeType) { SomeType variable = expression as SomeType; variable.SomeMethod(); } // ↓ // is演算子のみ if (expression is SomeType variable) { variable.SomeMethod(); } |
サンプルプログラム
コンソールアプリケーションを使って、is演算子とas演算子の動作を確認するサンプルプログラムを作成します。
ソースコード
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 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 |
using System; namespace ConsoleApp1 { // 基底クラス public class Base { public virtual void Method() { Console.WriteLine("This Method is BaseMethod."); } } // 派生クラス public class Derived : Base { public override void Method() { Console.WriteLine("This Method is Derived BaseMethod."); } } public class Program { // エントリーポイント private static void Main(string[] args) { // is演算子の例 IsOperatorExample(); // as演算子の例 AsOperatorExample(); } // is演算子の例 private static void IsOperatorExample() { object b = new Base(); Console.WriteLine(b is Base); Console.WriteLine(b is Derived); object d = new Derived(); Console.WriteLine(d is Base); Console.WriteLine(d is Derived); if (b is Base b2) { b2.Method(); } if (d is Base b3) { b3.Method(); } } // as演算子の例 private static void AsOperatorExample() { object b = new Base(); if (b is Base) { var b2 = b as Base; b2.Method(); } object d = new Derived(); if (d is Base) { var b2 = b as Base; b2.Method(); } } } } |
サンプルプログラムの実行
作成したプロジェクトをビルドして実行(デバッグ)します。
is演算子を使って基底クラス(Base)にキャストした場合と、as演算子を使って基底クラス(Base)にキャストした場合では、メソッドの実行結果が異なります。is演算子でのキャストでは、Derivedクラスのメソッドが呼び出されますが、as演算子でのキャストでは、Baseクラスのメソッドが呼び出されます。
1 2 3 4 5 6 7 8 |
True False True True This Method is BaseMethod. This Method is Derived BaseMethod. This Method is BaseMethod. This Method is BaseMethod. |
6行目がis演算子でキャストした結果、8行目がas演算子でキャストした結果。