質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

インターフェース

インターフェイスという用語はハードウェア・ソフトウェアの両方に使うことができます。 一般的に、インターフェイスは内部処理の詳細を見せないように設定されます。オブジェクト指向プログラミングにおいて、インターフェイスはabstractクラスとして定義されます。

Q&A

解決済

4回答

8308閲覧

「IList」と「List」の使い分け

saitokenshi

総合スコア5

C#

C#はマルチパラダイムプログラミング言語の1つで、命令形・宣言型・関数型・ジェネリック型・コンポーネント指向・オブジェクティブ指向のプログラミング開発すべてに対応しています。

インターフェース

インターフェイスという用語はハードウェア・ソフトウェアの両方に使うことができます。 一般的に、インターフェイスは内部処理の詳細を見せないように設定されます。オブジェクト指向プログラミングにおいて、インターフェイスはabstractクラスとして定義されます。

1グッド

2クリップ

投稿2020/10/08 06:03

編集2020/10/08 06:04

##背景状況
https://qiita.com/laughter/items/e9cf666e0430acc39e95
こちらの記事を読んでいたところ、冒頭に、

c#

1class Hoge 2{ 3 private readonly IList<int> _list = new List<int>(); 4}

という記述がありました。
これまで自分は「List<int>」などは頻繁に使っていましたが、「IList<int>」という宣言は使ったことがなく、困惑しました。

##知りたいこと
以下、ご回答頂けると嬉しいです。よろしくお願いいたします。

######1.なぜインターフェース型の変数などというものが宣言可能なのか
自分の理解では、インターフェースとはあくまでも実装の型宣言のみしかしておらず、具体的な実装が入っていない「もぬけの殻」であり、実運用のためには必ず当該インターフェースを実装したクラスを作る必要がある、と考えていました。

######2.インターフェース型変数を用いることのメリットは何か
List<T>型ではなく、あえてIList<T>を使うと、何が良いのか。

ams2020👍を押しています

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答4

0

ベストアンサー

Microsoft の「プログラミング C#」という本に書いてあったことの受け売りですが、インターフェースというのは何かを一言で表していて、自分的に一番分かりやすいと思った部分の抜粋を参考に書いておきます。

"インターフェイスというのは異なるコード間で交わされる契約である、といえます。このため、インターフェイスが定義されており、そして、あるクラスがそのインターフェースを実装していることを宣言していれば、そのクラスのクライアントはインターフェース内部に定義されているすべてのメソッドが確実に実装されていることが保証されます。"

(マーカーインターフェイスというのがあって上記とは違うのですが、それはちょっと置いときます)

C# はクラスの多重継承をサポートしていませんが、インターフェースは可能です。例えば、今回の質問の List<T> 型は以下のように多数のインターフェースを継承しています。

イメージ説明

1.なぜインターフェース型の変数などというものが宣言可能なのか
自分の理解では、インターフェースとはあくまでも実装の型宣言のみしかしておらず、具体的な実装が入っていない「もぬけの殻」であり、実運用のためには必ず当該インターフェースを実装したクラスを作る必要がある、と考えていました。

インターフェースは参照型です。それを定義して(または、IList<T> のようにフレームワークで定義済みならば)変数として宣言すれば、それを継承しているクラスのオブジェクト(インスタンス)への参照を格納可能です。

ただし、インターフェースからはオブジェクト(インスタンス)は生成できません。インターフェースを継承したクラスにインターフェイス内に定義されているメソッドを実装して、そのクラスからオブジェクトを生成することになります。

2.インターフェース型変数を用いることのメリットは何か
List<T>型ではなく、あえてIList<T>を使うと、何が良いのか。

使い方によっては「メリット」とは言えないかもしれませんが・・・

例えば上の画像の例で言うと List<T> が継承している ICollection 型の変数に List<T> 型オブジェクトへの参照を代入できます。

逆に、質問で参考にしているコード例では、_list には、例えば質問者さんが IList<T> を継承してカスタムクラスを定義したとすると、そのカスタムクラスのオブジェクト(インスタンス)を作成してそれへの参照を代入することができます。

オブジェクト指向でのカプセル化、継承、多態性・・・とはちょっと違うかもしれませんが、その流れから来ているような気がします。

投稿2020/10/09 03:32

退会済みユーザー

退会済みユーザー

総合スコア0

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

saitokenshi

2020/10/09 05:29

ありがとうございます!かなりイメージ進んだ気がします。 すいません、疑問点がいくつかあるので追加で質問よろしいでしょうか。 >フレームワークで定義済みならば この「定義」とは具体的にはどのようなことを指すのでしょうか。 >インターフェースを継承したクラスにインターフェイス内に定義されているメソッドを実装して、そのクラスからオブジェクトを生成することになります。 これはつまり、 private readonly IList<int> _list = new IList<int>(); (new List<int> → newIList<int> に変更したもの) ということはできないということでしょうか。
退会済みユーザー

退会済みユーザー

2020/10/09 06:09

> この「定義」とは具体的にはどのようなことを指すのでしょうか。 C# interface 定義 あたりをキーワードにググればいろいろヒットするので調べてみましょう。例えば下記: インターフェイス (C# プログラミング ガイド) https://docs.microsoft.com/ja-jp/dotnet/csharp/programming-guide/interfaces/ 上の記事の例では IEquatable<T> というインターフェースを定義しています。 > private readonly IList<int> _list = new IList<int>(); > (new List<int> → newIList<int> に変更したもの) > ということはできないということでしょうか。 (new List<int> → newIList<int> に変更したもの) というのは、何か私の想像の斜め上のことを考えているようで、意味不明です。 何にせよ、インターフェースからインスタンスは作れないということです。
saitokenshi

2020/10/10 09:06

混乱させてしまって申し訳ありませんでしたが、 > インターフェースからインスタンスは作れない はい、このように理解できました。「定義」に関しても勉強します。 ご回答ありがとうございました!
guest

0

1.なぜインターフェース型の変数などというものが宣言可能なのか

自分の理解では、インターフェースとはあくまでも実装の型宣言のみしかしておらず、

はい

具体的な実装が入っていない「もぬけの殻」であり、

はい

実運用のためには必ず当該インターフェースを実装したクラスを作る必要がある、と考えていました。

「実運用」の指すところが曖昧ですが、使う側からしたら、「この型にはこういう名前、引数、返り値のメソッドがある」だけわかってればいいので、変数の型がインターフェースであっても何ら問題ありません。もちろん、その変数の中身は実装クラスである必要があります。
そしてList<T>IList<T>を実装しています。

というか、インターフェース型の変数(メソッドの引数含む)を使わないなら
インターフェースを使う意味がありません。

2.インターフェース型変数を用いることのメリットは何か

List<T>型ではなく、あえてIList<T>を使うと、何が良いのか。

例のコードだとprivate readonlyで、List<int>を固定で代入しているので
正直あまり意味はないですが、
それでも、「IList<int>で宣言されているメソッドしか使わない」という意思表示にはなります。

投稿2020/10/08 07:31

編集2020/10/08 07:44
ozwk

総合スコア13528

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

saitokenshi

2020/10/09 05:21 編集

詳細にご回答ありがとうございます! >実運用 たしかに曖昧でした。キチンと言語化できているか怪しいですが、意図するところは、オブジェクト生成、変数作成などのことを指しました。 今回のケースでは、まさしく private readonly IList<int> _list = new List<int>(); ここの「_listを作成すること=実運用すること」という文脈になります。
guest

0

1.なぜインターフェース型の変数などというものが宣言可能なのか

只の入れ物のようなものなので、宣言は出来ます。

2.インターフェース型変数を用いることのメリットは何か

IListを実装している型なら格納できるので、汎用的が上がるからです。(例えば、配列もIListです)
インターフェースによってアクセス方法が共通化されているので、IListでアクセスする分には、中がList、配列、はたまた何か別のIList実装クラスか等を意識する必要が無くなります。

投稿2020/10/08 06:11

編集2020/10/08 06:24
退会済みユーザー

退会済みユーザー

総合スコア0

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

saitokenshi

2020/10/09 05:17

理解を進めることができました。ご回答ありがとうございます!
guest

0

質問内容より、そもそもインタフェイスというものを理解されていないと思われるので、個別の疑問を潰すよりもまず体系的に学習されることをお勧めします。

インターフェイス (C# プログラミング ガイド) - Microsoft
[オブジェクト指向] インターフェース - ++C++; // 未確認飛行 C

投稿2020/10/08 09:58

gentaro

総合スコア8949

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

saitokenshi

2020/10/09 05:21

ご回答ありがとうございます、併せて読んでいきたいと思います!
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問