はじめに
プログラミングにおける「インターフェース」について、自分の備忘録として記載しておきます。
言語はC#になります。
インターフェースの定義の記述
クラスにどんなメソッドやプロパティを実装するかの形だけ定め、実装は継承先の子クラスで行うもの。
namespace IFPlactice
{
interface ICharQueue
{
void Enqueue(char ch);
char Dequeue();
}
}
上記はchar型データのFIFOのキューを実装するインターフェースです。エンキュー/デキューのメソッドの定義がありますが、この実装は子クラスで行うことになります。
継承先での実装
インターフェースを継承してメソッドの処理内容を記述してみます。違う記述をしたFIFOのキュークラスを2つ作成してみます。
using System;
namespace IFPlactice
{
class SimpleQueue : ICharQueue
{
char[] queue;
int putIndex, getIndex;
public SimpleQueue(int inputQueueSize)
{
putIndex = 0;
getIndex = 0;
if (inputQueueSize > 0)
{
queue = new char[inputQueueSize];
}
else
{
queue = new char[10];
}
}
public void Enqueue(char ch)
{
if (putIndex < queue.Length)
{
queue[putIndex] = ch;
putIndex++;
}
else
{
Console.WriteLine("Simple Queue is Full.");
}
}
public char Dequeue()
{
if ((getIndex < queue.Length) && (getIndex < putIndex))
{
char retCh = queue[getIndex];
getIndex++;
return retCh;
}
else
{
Console.WriteLine("Simple Queue is Empty.");
return (char)0;
}
}
}
}
using System.Collections.Generic;
namespace IFPlactice
{
class ListQueue : ICharQueue
{
List<char> queue;
public ListQueue()
{
queue = new List<char>();
}
public void Enqueue(char ch)
{
queue.Add(ch);
}
public char Dequeue()
{
char ch = (char)0;
if (queue.Count > 0)
{
ch = queue[0];
queue.RemoveAt(0);
}
return ch;
}
}
}
片方はchar型の配列を作成し、古い順にデキューするクラスSimpleQueue、もう一つはList型のコレクションを使用してFIFOのキュー処理を実装するクラスListQueueになります。
両クラスとも同じインターフェースを継承し、Enqueue()、Dequeue()メソッドを実装していますが、その処理内容は大きく異なります。
インターフェース参照
継承先でメソッド等の処理内容をそれぞれ実装することができるメリットとして、インターフェース参照ができることが挙げられます。
インターフェース型の変数を用意し、対象のインターフェースを実装する任意のオブジェクトを参照することで、メソッド呼び出しを行うと参照先のオブジェクトに実装された形でメソッドを実行することができます。
先ほどのSimpleQueue、ListQueueを用いて実例を示します。
using System;
namespace IFPlactice
{
class IFPlacticeMain
{
static void Main()
{
SimpleQueue sq = new SimpleQueue(10);
ListQueue lq = new ListQueue();
// インターフェース参照用変数
ICharQueue iq;
// SimpleQueueオブジェクトを参照する
iq = sq;
char tempCh;
int i;
for (i = 0; i < 10; i++)
{
// 参照先のクラスを意識せずメソッドを呼びだせる
iq.Enqueue((char)('A' + i));
}
Console.Write("Simple Queue :");
for (i = 0; i < 10; i++)
{
// 参照先のクラスを意識せずメソッドを呼びだせる
tempCh = iq.Dequeue();
Console.Write(tempCh);
}
Console.WriteLine();
// ListQueueオブジェクトを参照する
iq = lq;
for (i = 0; i < 10; i++)
{
// 参照先のクラスを意識せずメソッドを呼びだせる
iq.Enqueue((char)('A' + i));
}
Console.Write("List Queue :");
for (i = 0; i < 10; i++)
{
// 参照先のクラスを意識せずメソッドを呼びだせる
tempCh = iq.Dequeue();
Console.Write(tempCh);
}
Console.WriteLine();
}
}
}
オブジェクトのクラスを意識することなくメソッド呼び出しが出来ました。なお、実行すると以下の様になります。
Simple Queue :ABCDEFGHIJ
List Queue :ABCDEFGHIJ
続行するには何かキーを押してください . . .
インターフェースと抽象クラス
後日記載・・・できればいいな・・・(汗