Как вернуть копию коллекции только для чтения - PullRequest
13 голосов
/ 12 мая 2009

У меня есть класс, который содержит коллекцию. Я хочу предоставить метод или свойство, которое возвращает содержимое коллекции. Это нормально, если вызывающие классы могут изменять отдельные объекты, но я не хочу, чтобы они добавляли или удаляли объект из фактической коллекции. Я копировал все объекты в новый список, но теперь я думаю, что мог бы просто вернуть список как IEnumerable <>.

В приведенном ниже упрощенном примере GetListC - лучший способ вернуть версию коллекции только для чтения?

public class MyClass
{
    private List<string> mylist;

    public MyClass()
    {
        mylist = new List<string>();
    }

    public void Add(string toAdd)
    {
        mylist.Add(toAdd);
    }

    //Returns the list directly 
    public List<String> GetListA 
    { 
        get
            {
            return mylist;
            }
    }

    //returns a copy of the list
    public List<String> GetListB
    {
        get
        {
            List<string> returnList = new List<string>();

            foreach (string st in this.mylist)
            {
                returnList.Add(st);
            }
            return returnList;
        }
    }

    //Returns the list as IEnumerable
    public IEnumerable<string> GetListC
    {
        get 
        {
            return this.mylist.AsEnumerable<String>();
        }

    }

}

Ответы [ 4 ]

26 голосов
/ 12 мая 2009

Вы можете использовать List(T).AsReadOnly():

return this.mylist.AsReadOnly()

, который вернет ReadOnlyCollection.

2 голосов
/ 12 мая 2009

Просто используйте класс ReadOnlyCollection, он поддерживается начиная с .NET 2.0

0 голосов
/ 12 мая 2009

Я предпочитаю возвращать IEnumerable, но вам не нужно кастовать Просто сделай

public IEnumerable<string> StringList { get { return myList; }

List<string> является IEnumerable<string>

0 голосов
/ 12 мая 2009

Используйте универсальный класс ReadOnlyCollection (Collection.AsReadOnly()). Он не копирует объекты, которые могут иметь странные результаты при изменении базовой коллекции.

        var foo = new List<int> { 3, 1, 2 };
        var bar = foo.AsReadOnly();

        foreach (var x in bar) Console.WriteLine(x);

        foo.Sort();

        foreach (var x in bar) Console.WriteLine(x);

Но если вам не нужна копия, это лучшее решение.

...