Есть ли простой способ скопировать содержимое TDictionary в другой? - PullRequest
14 голосов
/ 20 марта 2012

Есть ли один метод или простой способ, как скопировать одно содержимое TDictionary в другое? Допустим, у меня есть следующие объявления

type
  TItemKey = record
    ItemID: Integer;
    ItemType: Integer;
  end;
  TItemData = record
    Name: string;
    Surname: string;
  end;
  TItems = TDictionary<TItemKey, TItemData>;

var
  // the Source and Target have the same types
  Source, Target: TItems;
begin
  // I can't find the way how to copy source to target
end;

и я хотел бы скопировать 1: 1 источник для цели. Есть ли такой способ для этого?

Спасибо!

Ответы [ 3 ]

23 голосов
/ 20 марта 2012

TDictionary имеет конструктор, который позволяет передавать другой объект коллекции, который создаст новый, скопировав содержимое оригинала.Это то, что вы ищете?

constructor Create(Collection: TEnumerable<TPair<TKey,TValue>>); overload;

Таким образом, вы бы использовали

Target := TItems.Create(Source);

И цель была бы создана как копия источника (или, по крайней мере, содержала бы все элементы в источнике)).

1 голос
/ 20 марта 2012

Если вы хотите пойти еще дальше, вот другой подход:

type
  TDictionaryHelpers<TKey, TValue> = class
  public
    class procedure CopyDictionary(ASource, ATarget: TDictionary<TKey,TValue>);
  end;

...implementation...

{ TDictionaryHelpers<TKey, TValue> }

class procedure TDictionaryHelpers<TKey, TValue>.CopyDictionary(ASource,
  ATarget: TDictionary<TKey, TValue>);
var
  LKey: TKey;
begin
  for LKey in ASource.Keys do
    ATarget.Add(LKey, ASource.Items[ LKey ] );
end;

использование в соответствии с вашим определением Ключ и Значение :

TDictionaryHelpers<TItemKey, TItemData>.CopyDictionary(LSource, LTarget);
0 голосов
/ 20 марта 2012

Я думаю, что это должно сработать:

var
  LSource, LTarget: TItems;
  LKey: TItemKey;
begin
  LSource := TItems.Create;
  LTarget := TItems.Create;
  try
    for LKey in LSource.Keys do 
      LTarget.Add(LKey, LSource.Items[ LKey ]);
  finally
    LSource.Free;
    LTarget.Free;
  end; // tryf
end;
...