web-dev-qa-db-ja.com

配列がIListを実装する理由

System.Arrayクラスの定義を参照してください

public abstract class Array : IList, ...

理論的には、私はこのビットを書いて幸せになることができるはずです

int[] list = new int[] {};
IList iList = (IList)list;

また、iListから任意のメソッドを呼び出すことができるはずです

 ilist.Add(1); //exception here

私の質問は、例外を受け取る理由ではなく、むしろなぜIListを実装するのか

133
oleksii

配列はインデックスによる高速アクセスを可能にし、IList/IList<T>は、これをサポートする唯一のコレクションインターフェイスです。おそらく、あなたの本当の質問は、「なぜインデクサーを備えた一定のコレクションのインターフェースがないのか」ということでしょう。そして、それに答えはありません。

コレクション用の読み取り専用インターフェイスもありません。また、インデクサーインターフェイスを備えた一定サイズ以上のものもありません。

IMOには、コレクションの機能に応じて、さらに(一般的な)コレクションインターフェイスがいくつか必要です。また、名前も異なるはずです。インデクサーを使用する場合のListは、本当に愚かなIMOです。

  • ただ列挙IEnumerable<T>
  • 読み取り専用だがインデクサーなし(.Count、.Contains、...)
  • サイズ変更可能ですが、インデクサーはありません。つまり、(Add、Remove、...)current ICollection<T>
  • インデクサー(indexer、indexof、...)で読み取り専用
  • インデクサー付きの一定サイズ(セッター付きインデクサー)
  • インデクサーを使用した可変サイズ(挿入、...)current IList<T>

現在のコレクションインターフェイスはデザインが悪いと思います。しかし、どのメソッドが有効であるかを示すプロパティを持っているので(これはこれらのメソッドのコントラクトの一部です)、置換の原則を破ることはありません。

89
CodesInChaos

ドキュメント for IListの備考セクションには、

IListはICollectionインターフェイスの子孫であり、すべての非ジェネリックリストの基本インターフェイスです。 IListの実装は、読み取り専用、固定サイズ、可変サイズの3つのカテゴリに分類されます。読み取り専用のIListは変更できません。固定サイズのIListでは、要素の追加または削除はできませんが、既存の要素の変更はできます。可変サイズのIListでは、要素の追加、削除、および変更が可能です。

明らかに、配列は固定サイズのカテゴリに分類されるため、インターフェイスの定義によって意味があります。

39
Brian Rasmussen

すべてのIListsが可変ではないためIList.IsFixedSizeおよびIList.IsReadOnly)、および配列は確かに固定サイズのリストのように動作します。

あなたの質問が本当に「non-genericインターフェースを実装する理由」である場合、答えはジェネリックが登場する前に存在していたということです。

17
Mehrdad

これは、読み取り専用コレクションをどのように処理するか、および配列が読み取り専用であるかどうかが明確ではなかった時代からの遺産です。 IListインターフェイスには、IsFixedSizeおよびIsReadOnlyフラグがあります。 IsReadOnlyフラグはコレクションをまったく変更できないことを意味し、IsFixedSizeはコレクションが変更を許可するがアイテムの追加または削除を許可しないことを意味します。

.Net 4.5の時点では、読み取り専用コレクションを操作するにはいくつかの「中間」インターフェースが必要であることが明らかでした。したがって、IReadOnlyCollection<T>およびIReadOnlyList<T>は紹介されました。

詳細について説明している素晴らしいブログ投稿は次のとおりです。 。NETの読み取り専用コレクション

4
Vladimir

IListインターフェイスの定義は、「インデックスによって個別にアクセスできるオブジェクトの非ジェネリックコレクションを表します」です。配列はこの定義を完全に満たしているため、インターフェイスを実装する必要があります。 Add()メソッドを呼び出すときの例外は「System.NotSupportedException:Collection was fixed size」であり、配列はその容量を動的に増やすことができないために発生しました。その容量は、配列オブジェクトの作成中に定義されます。

0
meir