What is the best way to clone/deep copy a .NET gen

2019-01-03 02:17发布

I've got a generic dictionary Dictionary that I would like to essentially make a Clone() of ..any suggestions.

10条回答
爷的心禁止访问
2楼-- · 2019-01-03 02:48

Binary Serialization method works fine but in my tests it showed to be 10x slower than a non-serialization implementation of clone. Tested it on Dictionary<string , List<double>>

查看更多
走好不送
3楼-- · 2019-01-03 02:48

This works fine for me

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

 List<Dictionary<string, string>> objCopy = new List<Dictionary<string, string>>(obj);
查看更多
走好不送
4楼-- · 2019-01-03 02:49

For .NET 2.0 you could implement a class which inherits from Dictionary and implements 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;
    }
}

You can then clone the dictionary simply by calling the Clone method. Of course this implementation requires that the value type of the dictionary implements ICloneable, but otherwise a generic implementation isn't practical at all.

查看更多
该账号已被封号
5楼-- · 2019-01-03 02:51

(Note: although the cloning version is potentially useful, for a simple shallow copy the constructor I mention in the other post is a better option.)

How deep do you want the copy to be, and what version of .NET are you using? I suspect that a LINQ call to ToDictionary, specifying both the key and element selector, will be the easiest way to go if you're using .NET 3.5.

For instance, if you don't mind the value being a shallow clone:

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

If you've already constrained T to implement ICloneable:

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

(Those are untested, but should work.)

查看更多
Animai°情兽
6楼-- · 2019-01-03 02:54

The best way for me is this:

Dictionary<int, int> copy= new Dictionary<int, int>(yourListOrDictionary);
查看更多
我欲成王,谁敢阻挡
7楼-- · 2019-01-03 02:56

Try this if key/values are ICloneable:

    public static Dictionary<K,V> CloneDictionary<K,V>(Dictionary<K,V> dict) where K : ICloneable where V : ICloneable
    {
        Dictionary<K, V> newDict = null;

        if (dict != null)
        {
            // If the key and value are value types, just use copy constructor.
            if (((typeof(K).IsValueType || typeof(K) == typeof(string)) &&
                 (typeof(V).IsValueType) || typeof(V) == typeof(string)))
            {
                newDict = new Dictionary<K, V>(dict);
            }
            else // prepare to clone key or value or both
            {
                newDict = new Dictionary<K, V>();

                foreach (KeyValuePair<K, V> kvp in dict)
                {
                    K key;
                    if (typeof(K).IsValueType || typeof(K) == typeof(string))
                    {
                        key = kvp.Key;
                    }
                    else
                    {
                        key = (K)kvp.Key.Clone();
                    }
                    V value;
                    if (typeof(V).IsValueType || typeof(V) == typeof(string))
                    {
                        value = kvp.Value;
                    }
                    else
                    {
                        value = (V)kvp.Value.Clone();
                    }

                    newDict[key] = value;
                }
            }
        }

        return newDict;
    }
查看更多
登录 后发表回答