.Net 【基础回顾】深浅复制

摘要

复制一直是面试喜欢问的问题,这里总结一下

浅复制与深复制

  • 浅copy:只复制引用,修改后对原来的变量有影响。

  • 深copy:复制引用和引用的对象,修改后对原来的变量没有影响

=复制

浅复制

  • 值类型:复制值,修改后对原来的变量没有影响

  • 引用类型:复制引用地址,修改后对原来的变量有影响

  • String: 跟着值类型走

MemberwiseClone

浅复制

Object的实例方法MemberwiseClone实现的是浅复制,注意是protected修饰,只能定义的继承类或者extension实现

protected Object MemberwiseClone();

深copy实现

  1. 反射

  2. 序列化反序列化,最简单

  3. 实现ICloneable接口Clone方法,手工复制对象的每一个field

通用实现

序列化


using System;
using System.IO;
using System.Runtime.Serialization.Formatters.Binary;

namespace DotnetDemo
{
    [Serializable]
    public class BaseClone<T>
    {
        public virtual T Clone()
        {
            using (var memoryStream = new MemoryStream())
            {
                var formatter = new BinaryFormatter();
                formatter.Serialize(memoryStream, this);
                memoryStream.Position = 0;
                return (T)formatter.Deserialize(memoryStream);
            }
        }
    } 
}


实现的demo

注意必须为相关类及类的引用类型加上可序列化标识:[Serializable]


using System;

namespace DotnetDemo
{
    public class CloneDemo
    {
        public void Test()
        {
            // 值类型

            var aa = 11;
            var bb = aa;
            bb = 22;

            Console.WriteLine(aa); //11

            // string

            var cc = "11";
            var dd = cc;
            dd = "22";

            Console.WriteLine(cc); //"11"

            // 引用类型

            var ee = new CloneDemoInfo() { ID = 11, ExtensionInfo = new ExtensionInfo() { Name = "Name" } };
            var ff = ee;
            var gg = ee.ShallowCopy();
           

           

            ff.ID = 22;
            ff.ExtensionInfo = new ExtensionInfo() { Name = "newName" };

            Console.WriteLine(ee.ID); // 22

            Console.WriteLine(ee.ExtensionInfo.Name); // newName

            var hh = ee.Clone();

            hh.ID = 33;
            hh.ExtensionInfo = new ExtensionInfo() { Name = "CloneName" };

            Console.WriteLine(ee.ID); // 22

            Console.WriteLine(ee.ExtensionInfo.Name); // newName

        }
    }

    [Serializable]
    public class ExtensionInfo
    {
        public string Name { get; set; }
    }

    [Serializable]
    public class CloneDemoInfo : BaseClone<CloneDemoInfo>
    {

        public int ID { get; set; } //值类型

        public ExtensionInfo ExtensionInfo { get; set; } //引用类型

        /// <summary>
        /// 浅复制
        /// </summary>
        /// <returns></returns>
        public CloneDemoInfo ShallowCopy()
        {
            return (CloneDemoInfo)this.MemberwiseClone();
        }


    }
}

posted on 2022-05-08 10:56  杏村牧童  阅读(44)  评论(0编辑  收藏  举报