.NET 일반 사전 <string, T>을 복제 / 딥 복사하는 가장 좋은 방법은 무엇입니까? Clone ()을 만들고 싶은

Dictionary<string, T>본질적으로 .. 모든 제안의 Clone ()을 만들고 싶은 일반 사전 이 있습니다.



답변

좋아, .NET 2.0 답변 :

값을 복제 할 필요가 없으면 생성자 오버로드를 기존 IDictionary를 사용하는 Dictionary에 사용할 수 있습니다. 비교자를 기존 사전의 비교 자로 지정할 수도 있습니다.

당신이 경우 않는 값을 복제 할 필요가, 당신은 이런 식으로 뭔가를 사용할 수 있습니다 :

public static Dictionary<TKey, TValue> CloneDictionaryCloningValues<TKey, TValue>
   (Dictionary<TKey, TValue> original) where TValue : ICloneable
{
    Dictionary<TKey, TValue> ret = new Dictionary<TKey, TValue>(original.Count,
                                                            original.Comparer);
    foreach (KeyValuePair<TKey, TValue> entry in original)
    {
        ret.Add(entry.Key, (TValue) entry.Value.Clone());
    }
    return ret;
}

물론 그것은 TValue.Clone()물론 깊게 깊은 클론 에 의존합니다 .


답변

(참고 : 복제 버전이 유용 할 수는 있지만 간단한 얕은 사본의 경우 다른 게시물에서 언급 한 생성자가 더 나은 옵션입니다.)

복사본을 얼마나 깊이 원하십니까? 그리고 사용중인 .NET 버전은 무엇입니까? .NET 3.5를 사용하는 경우 키와 요소 선택기를 모두 지정하는 ToDictionary에 대한 LINQ 호출이 가장 쉬운 방법이라고 생각합니다.

예를 들어, 값이 얕은 복제본이 아니라면

var newDictionary = oldDictionary.ToDictionary(entry => entry.Key,
                                               entry => entry.Value);

ICloneable을 구현하도록 T를 이미 제한 한 경우 :

var newDictionary = oldDictionary.ToDictionary(entry => entry.Key,
                                               entry => (T) entry.Value.Clone());

(테스트되지는 않았지만 작동해야합니다.)


답변

Dictionary<string, int> dictionary = new Dictionary<string, int>();

Dictionary<string, int> copy = new Dictionary<string, int>(dictionary);


답변

.NET 2.0의 경우을 상속하고 구현하는 클래스를 Dictionary구현할 수 ICloneable있습니다.

public class CloneableDictionary<TKey, TValue> : Dictionary<TKey, TValue> where TValue : ICloneable
{
    public IDictionary<TKey, TValue> Clone()
    {
        CloneableDictionary<TKey, TValue> clone = new CloneableDictionary<TKey, TValue>();

        foreach (KeyValuePair<TKey, TValue> pair in this)
        {
            clone.Add(pair.Key, (TValue)pair.Value.Clone());
        }

        return clone;
    }
}

그런 다음 단순히 Clone메소드 를 호출하여 사전을 복제 할 수 있습니다 . 물론이 구현은 딕셔너리의 값 유형이 구현을 요구 ICloneable하지만, 그렇지 않으면 일반적인 구현은 전혀 실용적이지 않습니다.


답변

이것은 나를 위해 잘 작동

 // assuming this fills the List
 List<Dictionary<string, string>> obj = this.getData();

 List<Dictionary<string, string>> objCopy = new List<Dictionary<string, string>>(obj);

주석에서 Tomer Wolberg가 설명했듯이 값 유형이 변경 가능한 클래스 인 경우 작동하지 않습니다.


답변

항상 직렬화를 사용할 수 있습니다. 객체를 직렬화 한 다음 역 직렬화 할 수 있습니다. 그러면 사전과 그 안의 모든 항목에 대한 깊은 사본이 제공됩니다. 이제 특수 코드를 작성하지 않고 [Serializable]로 표시된 모든 객체의 딥 카피를 만들 수 있습니다.

이진 직렬화를 사용하는 두 가지 방법이 있습니다. 이 방법을 사용하면 간단히 전화하십시오.

object deepcopy = FromBinary(ToBinary(yourDictionary));

public Byte[] ToBinary()
{
  MemoryStream ms = null;
  Byte[] byteArray = null;
  try
  {
    BinaryFormatter serializer = new BinaryFormatter();
    ms = new MemoryStream();
    serializer.Serialize(ms, this);
    byteArray = ms.ToArray();
  }
  catch (Exception unexpected)
  {
    Trace.Fail(unexpected.Message);
    throw;
  }
  finally
  {
    if (ms != null)
      ms.Close();
  }
  return byteArray;
}

public object FromBinary(Byte[] buffer)
{
  MemoryStream ms = null;
  object deserializedObject = null;

  try
  {
    BinaryFormatter serializer = new BinaryFormatter();
    ms = new MemoryStream();
    ms.Write(buffer, 0, buffer.Length);
    ms.Position = 0;
    deserializedObject = serializer.Deserialize(ms);
  }
  finally
  {
    if (ms != null)
      ms.Close();
  }
  return deserializedObject;
}


답변

나에게 가장 좋은 방법은 다음과 같습니다.

Dictionary<int, int> copy= new Dictionary<int, int>(yourListOrDictionary);