背景:简历上显示某人姓名性别及工作经历。
浅复制:
工作经历类:
class WorkExperience { private string workDate; public string WorkDate { get { return workDate; } set { workDate = value; } } private string company; public string Company { get { return company; } set { company = value; } } }简历类:
class Resume:ICloneable { private string name; private string age; private string sex; public void SetPersonalInfo(string sex, string age)//设置个人信息 { this.sex = sex; this.age = age; } public void SetWorkExperience(string workDate, string company) { work.WorkDate = workDate; work.Company = company; } //显示 public void Display() { Console.WriteLine("{0} {1} {2}", name, sex, age); Console.WriteLine("工作经历:{0} {1}", work.WorkDate, work.Company); } public Object Clone() { return (Object)this.MemberwiseClone(); } private WorkExperience work;//引用工作经历对象 public Resume(string name) { this.name = name; work = new WorkExperience(); } }客户端代码:
class Program { static void Main(string[] args) { Resume a = new Resume("小明"); a.SetPersonalInfo("男", "29"); a.SetWorkExperience("1998-2000", "xx公司"); Resume b = (Resume)a.Clone(); b.SetWorkExperience("1998-2006", "yy公司"); Resume c = (Resume)a.Clone(); c.SetPersonalInfo("男", "24"); a.Display(); b.Display(); c.Display(); Console.Read(); } }结果:
浅复制中简历类引用工作经历对象,MemberwiseClone()方法,如果字段是值类型的(如int double char等等)的,则对该字段执行逐位复制,如果字段是引用类型,则复制引用但不复制引用的对象,因此,原始对象及其复本引用同一对象。既可以看到结果中,年龄性别等值类型的可以显示不同的结果,而“工作经历”这一项是一样的。
深复制:
找不同:
让“工作经历”实现ICloneable接口,在“工作经历”类中实现克隆方法
class WorkExperience:ICloneable { }
提供clone方法调用的私有构造函数,以便克隆“工作经历”的数据,有了这一步,之前的引用类型的工作经历就被复制了。
private Resume (WorkExperience work) { this.work = (WorkExperience)work.Clone(); }最后,调用私有的构造方法,让“工作经历”克隆完成,然后给这个简历对象的相关字段赋值,最终返回一个简历对象。
public Object Clone() { //return (Object)this.MemberwiseClone(); Resume obj = new Resume(this.work); obj.name = this.name; obj.sex = this.sex; obj.age = this.age; return obj; }
深复制是把引用对象的变量指向复制过的新对象,而不是原有的被引用对象。这样得到的结果工作经历也指向新对象了,与浅复制的区别显而易见。