1.简历复印
先用一个基本的简历类如下(注:本文示例均引用于《大话设计模式》)
using System;
using System.Collections.Generic;
using System.Text;
namespace Resume
{
class Resume
{
private string name;
private string sex;
private string age;
private string timeArea;
private string company;
public Resume(string name)
{
this.name=name;
}
public void SetPersonalInfo(string sex, string age)
{
this.sex = sex;
this.age = age;
}
public void SetWorkExperience(string timeArea, string company)
{
this.timeArea = timeArea;
this.company = company;
}
public void Diaplay()
{
Console.WriteLine("{0} {1} {2}", name, sex, age);
Console.WriteLine("工作经历: {0} {1}", timeArea, company);
}
}
}
如果要复印多份简历,客户端代码如下:
static void Main(string[] args)
{
Resume a = new Resume("大鸟");
a.SetPersonalInfo("男", "29");
a.SetWorkExperience("1998-2000", "XX公司");
Resume b = a;
Resume c = a;
a.Diaplay();
b.Diaplay();
c.Diaplay();
Console.Read();
}
不过,此种方法传的是引用,而不是值,a,b,c其实还是同一份简历。
2.原型模式
我们可以用原型模式(Prototype),所謂原型模式,是指从一个对象创建另外一个可定制的对象,而且我们不需要知道任何创建的细节.
.NET在System命名空间中提供了ICloneable接口,这个接口中只有唯一一个方法Clone().我们只需要实现ICloneable这个接口即可实现原型模式.
WorkExperience类是"工作经历"原型类代码如下:
class WorkExperience:ICloneable
{
private string workDate;
public string WorkDate
{
get { return workDate; }
set { workDate = value; }
}
private string company;
public string Company
{
get { return company; }
set { company = value; }
}
public Object Clone()
{
return (object)this.MemberwiseClone();
}
}
在简历类中用"this.work = (WorkExperience)work.Clone();"语句即可实现原型类的克隆.
3.浅复制和深复制:
1) 浅复制
MemberwiseClone()方法引用的字段如果是值类型的,则对该字段进行逐位复制;如果字段是引用类型,则复制引用但不复制引用的对象.
即原始对象及其复本引用同一对象.
当不同的复本的引用值改变时,原始对象及所有复本的引用值都会改变.这就是浅复制.
2) 深复制
当我们希望不同的复本的引用值有所区别时,就要使用深复制.
深复制把引用对象的变量指向复制过的新对象,而不是原有的被引用的对象.
如示例中复制简历时,工作经历就相当于一个引用对象.可以对简历类的Clone()方法做些改变.
如下所示,调用简历类中私有的构造方法,克隆工作经历,这样就实现了深复制.
public object Clone()
{
Resume obj = new Resume(this.work);
obj.name = this.name;
obj.sex = this.sex;
obj.age = this.age;
return obj;
}
完整代码如下所示:
using System;
using System.Collections.Generic;
using System.Text;
namespace Resume
{
public class Resume: ICloneable
{
private string name;
private string sex;
private string age;
private WorkExperience work;
public Resume(string name)
{
this.name=name;
work = new WorkExperience();
}
private Resume(WorkExperience work)
{
this.work = (WorkExperience)work.Clone();
}
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 Diaplay()
{
Console.WriteLine("{0} {1} {2}", name, sex, age);
Console.WriteLine("工作經歷: {0} {1}", work.WorkDate, work.Company);
}
public object Clone()
{
Resume obj = new Resume(this.work);
obj.name = this.name;
obj.sex = this.sex;
obj.age = this.age;
return obj;
}
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");
c.SetWorkExperience("1998-2006", "ZZ企業");
a.Diaplay();
b.Diaplay();
c.Diaplay();
Console.Read();
}
}
}