Как скопировать элементы из списка в список без foreach?


319

Как я могу передать элементы, содержащиеся Listв C #, без использования foreach?


3
Если вам нужен глубокий клон оригинального списка, вы найдете ответ на этот связанный вопрос: stackoverflow.com/questions/222598/…
Дирк Воллмар,

Ответы:


555

Вы можете попробовать это:

List<Int32> copy = new List<Int32>(original);

или если вы используете C # 3 и .NET 3.5 с Linq, вы можете сделать это:

List<Int32> copy = original.ToList();

14
Если элементы относятся к типу, MyClassа Integerне к ним, копирует ли он элементы или просто ссылается на них?
Педро Морейра

6
Не работает с не примитивными типами. List <StudentClass> copy = new List <StudentClass> (lstStudentClass);
кричать

4
Он работает со всеми типами, до тех пор , как lstStudentClassэто IEnumerable<StudentClass>, он будет работать. Если вы испытываете иное, вам нужно предоставить больше информации.
Лассе В. Карлсен

1
что означает (оригинал); в конце
Рахул Чаудхари

1
Вы передаете коллекцию конструктору списка, и конструктор затем скопирует все элементы этой коллекции во вновь созданный список.
Лассе В. Карлсен

170

Чтобы добавить содержимое одного списка в другой, который уже существует, вы можете использовать:

targetList.AddRange(sourceList);

Если вы просто хотите создать новую копию списка, посмотрите ответ Лассе.


6
@mrmillsy: Ну, они делают разные вещи. Мой ответ сфокусирован на том, что «у меня уже есть список, и я хочу скопировать в него что-то»
Джон Скит

Правда. Мой вопрос, вероятно, будет лучше соответствовать новому вопросу в любом случае. Спасибо за ответ, хотя.
mrmillsy

1
Если вы хотите полностью заменить содержимое существующего списка, вы должны сначала вызвать targetList.Clear ().
Ибрагим

33

Для списка элементов

List<string> lstTest = new List<string>();

lstTest.Add("test1");
lstTest.Add("test2");
lstTest.Add("test3");
lstTest.Add("test4");
lstTest.Add("test5");
lstTest.Add("test6");

Если вы хотите скопировать все элементы

List<string> lstNew = new List<string>();
lstNew.AddRange(lstTest);

Если вы хотите скопировать первые 3 элемента

List<string> lstNew = lstTest.GetRange(0, 3);

5

И это если необходимо скопировать одно свойство в другой список:

targetList.AddRange(sourceList.Select(i => i.NeededProperty));

4

Этот метод создаст копию вашего списка, но ваш тип должен быть сериализуемым.

Использование:

List<Student> lstStudent = db.Students.Where(s => s.DOB < DateTime.Now).ToList().CopyList(); 

Метод:

public static List<T> CopyList<T>(this List<T> lst)
    {
        List<T> lstCopy = new List<T>();
        foreach (var item in lst)
        {
            using (MemoryStream stream = new MemoryStream())
            {
                BinaryFormatter formatter = new BinaryFormatter();
                formatter.Serialize(stream, item);
                stream.Position = 0;
                lstCopy.Add((T)formatter.Deserialize(stream));
            }
        }
        return lstCopy;
    }

Создает ли сериализация существенное снижение производительности?
Dan Def

0

ОК, это работает хорошо. Из приведенных выше предложений GetRange () не работает для меня со списком в качестве аргумента ... так что немного подсластите посты выше: (спасибо всем :)

/*  Where __strBuf is a string list used as a dumping ground for data  */
public List < string > pullStrLst( )
{
    List < string > lst;

    lst = __strBuf.GetRange( 0, __strBuf.Count );     

    __strBuf.Clear( );

    return( lst );
}

2
Это даже не ответ.
Мацей Юречко

ммм ... ладно, некоторые из вышеперечисленных предложений просто не работают в Vis 17. Я убрал лучший ответ при условии ... и эй предыстория ... это работает :)
Джим Стивенс

0

Легко отобразить другой набор списка по linq без цикла for

var List1= new List<Entities1>();

var List2= new List<Entities2>();

var List2 = List1.Select(p => new Entities2
        {
            EntityCode = p.EntityCode,
            EntityId = p.EntityId,
            EntityName = p.EntityName
        }).ToList();

-9

Здесь другой метод, но он немного хуже по сравнению с другим.

List<int> i=original.Take(original.count).ToList();

24
Почему ты бы так поступил? Почему не ToList()напрямую?
nawfal
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.