2010-04-09 3 views
2

У меня есть небольшое требование при объединении списков. Я попытаюсь проиллюстрировать пример. Допустим, я работаю с 2 списками объектов GamePlayer. У GamePlayer есть свойство LastGamePlayed. Уникальный GamePlayer идентифицируется через свойство GamePlayer.ID. Теперь я хотел бы объединить listA и listB в один список, и если данный игрок присутствует в обоих списках, я хотел бы сохранить значение из списка A.Объединение списков, но получение уникальных членов

Я не могу просто комбинировать списки и использовать компаратор, потому что моя уникальность основана на ID, и если мой идентификатор сравнения проверяет идентификатор, я не буду контролировать, выбирает ли он элемент listA или listB. Мне нужно что-то вроде:

for each player in listB 
{ 
    if not listA.Contains(player) 
    { 
     listFinal.Add(player) 
    } 
} 

Однако, есть более оптимальный способ сделать это вместо того, чтобы искать lišta для каждого элемента в LISTB?

**** EDIT ****: В противном случае, если бы я хотел выбрать, какой GamePlayer я буду использовать на основе значения LastGamePlayed (вместо того, чтобы знать, что ListA имеет преимущество перед ListB)? Итак, я хочу уникальный список объектов GamePlayer, но для каждого игрока я хочу, чтобы объект GamePlayer с последним LastGamePlayed? В основном мне нужен способ определить, какой объект хранить, когда есть дубликаты GamePlayers.

+0

В этом случае listFinal будет содержать все listA и все элементы из спискаB, которых нет в спискеA? – Thomas

ответ

1

Теперь, когда это было выяснено, вопрос в основном это:

  • Объединить все элементы из списка А и список В, и если есть какие-либо дубликаты, сохранить один с новейшими LastGamePlayed.

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

var players = from p in listA.Concat(listB) 
       group p by p.ID into g 
       select g.OrderByDescending(x => x.LastGamePlayed).First(); 

Если производительность является проблемой, есть «быстрые» способы написать это, но я хотел бы начать с этого.

2

Вы должны иметь возможность использовать перечислимое расширение linq Concat и Exept для достижения этого.

listA.Concat (listB.Except (lišta);

Это удалит элементы в B, которые соответствуют, а их сложат А.

Вы должны написать IEqualityComparer, который сравнит . по ID

Документация к методам тезисов можно найти здесь:

MSDN Enumerable Extensions

IEqualityComp ARER документацию можно найти здесь:

MSDN IEqualityComparer

0

Вы можете написать O (п § п) решение путем создания набора из list2 затем перезаписать (или вставки) элементов с list1, а затем преобразовать этот набор обратно к список.

Если списки уже отсортированы, вы можете сделать это O (n) путем слияния вручную.

Смежные вопросы