ICollection<T>
类型。这是Entity Framework的强制要求吗?我能否使用
IEnumerable
?使用
ICollection
的主要目的是什么,相对于IEnumerable
或甚至List<T>
而言?ICollection<T>
类型。IEnumerable
?ICollection
的主要目的是什么,相对于IEnumerable
或甚至List<T>
而言?IEnumerable<>
(MSDN:http://msdn.microsoft.com/en-us/library/system.collections.ienumerable.aspx);对于需要迭代并修改的对象列表,使用 ICollection<>
(MSDN:http://msdn.microsoft.com/en-us/library/92t2ye13.aspx);对于需要迭代、修改、排序等的对象列表,使用 List<>
(有关完整列表,请参见此处:http://msdn.microsoft.com/en-us/library/6sh2ey19.aspx)。ICollection
。
有关定义和管理关系的更多信息MSDN。表示关系的“多”端的导航属性必须返回一个实现ICollection的类型,其中T是关系另一端的对象类型。-创建POCO代理的要求MSDN
private IEnumerable<int> _integers = new List<int> { 1, 2, 3 };
和 private List<int> _integers = new List<int> { 1, 2, 3 };
使用相同的内存。 - phoogList<T>
类有一个GetEnumerator()
方法,与其实现的IEnumerable<T>
接口分离,该方法返回可变结构类型List<T>.Enumerator
。在大多数情况下,该类型将比独立的堆对象提供稍微更好的性能。对于那些鸭式枚举器的编译器(如C#和vb.net),可以利用此功能生成foreach
代码。如果在foreach
之前将List<T>
强制转换为IEnumerable<T>
,则IEnumerable<T>.GetEnumerator()
方法将返回一个分配在堆上的对象,从而使优化无法实现。 - supercatICollection<T>
被使用是因为 IEnumerable<T>
接口没有提供添加、删除或修改集合的方法。
List<T>
实现了 ICollection<T>
。 - spenderICollection
接口不允许添加项,但它仍然是 IEnumerable<T>
的一个有用补充,因为它提供了一个 Count
成员,通常比枚举所有项要快得多。请注意,如果将一个 IList<Cat>
或 ICollection<Cat>
传递给期望一个 IEnumerable<Animal>
的代码,则如果它实现了非泛型的 ICollection
,则 Count()
扩展方法会很快,但如果它只实现了泛型接口,则不会,因为典型的 ICollection<Cat>
不会实现 ICollection<Animal>
。 - supercat针对您的问题有关于 List<T>
:
List<T>
是一个类,指定一个接口可以提供更多的实现灵活性。更好的问题是“为什么不用 IList<T>
?”
回答这个问题,考虑一下 IList<T>
相比 ICollection<T>
添加了什么:整数索引,这表示项目具有某种任意顺序,并且可以通过引用该顺序来检索它们。在大多数情况下,这可能没有意义,因为在不同的上下文中可能需要以不同的方式排序项目。
ICollection和IEnumerable之间有一些基本的差异
简单程序:
using System;
using System.Collections;
using System.Collections.Generic;
namespace StackDemo
{
class Program
{
static void Main(string[] args)
{
List<Person> persons = new List<Person>();
persons.Add(new Person("John",30));
persons.Add(new Person("Jack", 27));
ICollection<Person> personCollection = persons;
IEnumerable<Person> personEnumeration = persons;
// IEnumeration
// IEnumration Contains only GetEnumerator method to get Enumerator and make a looping
foreach (Person p in personEnumeration)
{
Console.WriteLine("Name:{0}, Age:{1}", p.Name, p.Age);
}
// ICollection
// ICollection Add/Remove/Contains/Count/CopyTo
// ICollection is inherited from IEnumerable
personCollection.Add(new Person("Tim", 10));
foreach (Person p in personCollection)
{
Console.WriteLine("Name:{0}, Age:{1}", p.Name, p.Age);
}
Console.ReadLine();
}
}
class Person
{
public string Name { get; set; }
public int Age { get; set; }
public Person(string name, int age)
{
this.Name = name;
this.Age = age;
}
}
}
我记得是这样的:
IEnumerable有一个GetEnumerator()方法,允许读取集合中的值但无法写入它。在C#中,使用foreach语句可以为我们处理大部分枚举器的复杂性。IEnumerable有一个属性:Current,它返回当前元素。
ICollection实现了IEnumerable并添加了一些额外的属性,其中最常用的是Count。泛型版本的ICollection实现了Add()和Remove()方法。
IList实现了IEnumerable和ICollection,并添加了整数索引访问项目的功能(通常不需要,因为排序是在数据库中完成的)。
ICollection
的基本思想是提供界面来只读地访问一些有限的数据。实际上,你有一个ICollection.Count 属性。IEnumerable
更适合于一些链式数据,您可以在那里阅读到某个逻辑点,某个由使用者明确指定的条件或枚举结束。ICollection
是只读的,而 ICollection<T>
则不是。 - Carl G当调用System.Collections.ICollection接口的方法和属性时,应在堆上执行动态内存分配和释放,但在调用System.Collections.IEnumerable接口的方法和属性时不应该执行(尽管System.Collections.IEnumerable接口只有1个方法和0个属性)。
根据其他人在此Stack Overflow网页上所说,System.Collections.IList接口仅表示可排序集合,这解释了为什么System.Collections.IList接口的方法使用索引,而System.Collections.ICollection接口的方法则不同。
简而言之,System.Collections.ICollection接口并不意味着它的实例是可排序的,但System.Collections.IList接口确实意味着它是可排序的。
理论上,有序集合是无序集合的特殊情况。
这也很有道理,解释了为什么System.Collections.IList接口继承System.Collections.ICollection接口。
void Load(object key)
void Load(IEnumerable keys)