返回“設計模式(C#)系列文章索引”
介紹
表示一個作用於某對象結構中的各元素的操作。它使你可以在不改變各元素的類的前提下定義作用於這些元素的新操作。
示例
有一個Message實體類,某些對象對它的操作有Insert()和Get()方法,現在要針對其中某一方法進行操作。
MessageModel
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// Message實體類
/// </summary>
public class MessageModel
{
/**//// <summary>
/// 構造函數
/// </summary>
/// <param name="msg">Message內容</param>
/// <param name="pt">Message發布時間</param>
public MessageModel(string msg, DateTime pt)
{
this._message = msg;
this._publishTime = pt;
}
private string _message;
/**//// <summary>
/// Message內容
/// </summary>
public string Message
{
get { return _message; }
set { _message = value; }
}
private DateTime _publishTime;
/**//// <summary>
/// Message發布時間
/// </summary>
public DateTime PublishTime
{
get { return _publishTime; }
set { _publishTime = value; }
}
}
}
AbstractElement
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// 抽象元素(Element)
/// </summary>
public abstract class AbstractElement
{
/**//// <summary>
/// 執行抽象訪問者的Visit()方法(從而執行抽象元素的方法)
/// </summary>
/// <param name="abstractVisitor">抽象訪問者</param>
/// <returns></returns>
public abstract string Accept(AbstractVisitor abstractVisitor);
}
}
Message
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// 操作Message抽象類(Element)
/// </summary>
public abstract class Message : AbstractElement
{
private MessageModel _messageModel;
/**//// <summary>
/// 構造函數
/// </summary>
/// <param name="mm">Message實體對象</param>
public Message(MessageModel mm)
{
this._messageModel = mm;
}
/**//// <summary>
/// Message實體對象
/// </summary>
public MessageModel MessageModel
{
get { return _messageModel; }
set { _messageModel = value; }
}
/**//// <summary>
/// 執行抽象訪問者的Visit()方法(從而執行抽象元素的方法)
/// </summary>
/// <param name="abstractVisitor">抽象訪問者</param>
/// <returns></returns>
public override string Accept(AbstractVisitor abstractVisitor)
{
return abstractVisitor.Visit(this);
}
/**//// <summary>
/// 獲取Message
/// </summary>
/// <returns></returns>
public abstract List<MessageModel> Get();
/**//// <summary>
/// 插入Message
/// </summary>
/// <returns></returns>
public abstract bool Insert();
}
}
SqlMessage
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// Sql方式操作Message(ConcreteElement)
/// </summary>
public class SqlMessage : Message
{
/**//// <summary>
/// 構造函數
/// </summary>
/// <param name="mm">Message實體對象</param>
public SqlMessage(MessageModel mm)
: base(mm)
{
}
/**//// <summary>
/// 獲取Message
/// </summary>
/// <returns></returns>
public override List<MessageModel> Get()
{
List<MessageModel> l = new List<MessageModel>();
l.Add(new MessageModel("SQL方式獲取Message", DateTime.Now));
return l;
}
/**//// <summary>
/// 插入Message
/// </summary>
/// <returns></returns>
public override bool Insert()
{
// 代碼略
return true;
}
}
}
XmlMessage
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// Xml方式操作Message(ConcreteElement)
/// </summary>
public class XmlMessage : Message
{
/**//// <summary>
/// 構造函數
/// </summary>
/// <param name="mm">Message實體對象</param>
public XmlMessage(MessageModel mm)
: base(mm)
{
}
/**//// <summary>
/// 獲取Message
/// </summary>
/// <returns></returns>
public override List<MessageModel> Get()
{
List<MessageModel> l = new List<MessageModel>();
l.Add(new MessageModel("XML方式獲取Message", DateTime.Now));
return l;
}
/**//// <summary>
/// 插入Message
/// </summary>
/// <returns></returns>
public override bool Insert()
{
// 代碼略
return true;
}
}
}
AbstractVisitor
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// 抽象訪問者(Visitor)
/// </summary>
public abstract class AbstractVisitor
{
/**//// <summary>
/// 執行抽象元素的方法
/// </summary>
/// <param name="abstractElement">抽象元素</param>
/// <returns></returns>
public abstract string Visit(AbstractElement abstractElement);
}
}
InsertVisitor
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// Insert訪問者(ConcreteVisitor)
/// </summary>
public class InsertVisitor : AbstractVisitor
{
/**//// <summary>
/// 執行Message的Insert()方法
/// </summary>
/// <param name="abstractElement">抽象元素</param>
/// <returns></returns>
public override string Visit(AbstractElement abstractElement)
{
Message m = abstractElement as Message;
return m.Insert().ToString() + "<br />";
}
}
}
GetVisitor
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// Get訪問者(ConcreteVisitor)
/// </summary>
public class GetVisitor : AbstractVisitor
{
/**//// <summary>
/// 執行Message的Get()方法
/// </summary>
/// <param name="abstractElement">抽象元素</param>
/// <returns></returns>
public override string Visit(AbstractElement abstractElement)
{
Message m = abstractElement as Message;
return m.Get()[0].Message + " " + m.Get()[0].PublishTime.ToString() + "<br />";
}
}
}
Messages
using System;
using System.Collections.Generic;
using System.Text;
namespace Pattern.Visitor
{
/**//// <summary>
/// Message集合(ObjectStructure)
/// </summary>
public class Messages
{
private List<Message> _list = new List<Message>();
/**//// <summary>
/// 添加一個Message對象
/// </summary>
/// <param name="message">Message對象</param>
public void Attach(Message message)
{
_list.Add(message);
}
/**//// <summary>
/// 移除一個Message對象
/// </summary>
/// <param name="message">Message對象</param>
public void Detach(Message message)
{
_list.Remove(message);
}
/**//// <summary>
/// 執行集合內所有Message對象的Accept()方法(執行抽象訪問者的Visit()方法(從而執行抽象元素的方法))
/// </summary>
/// <param name="abstractVisitor">抽象訪問者</param>
/// <returns></returns>
public string Accept(AbstractVisitor abstractVisitor)
{
string s = "";
foreach (Message m in _list)
{
s += m.Accept(abstractVisitor);
}
return s;
}
}
}
Test
using System;
using System.Data;
using System.Configuration;
using System.Collections;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;
using Pattern.Visitor;
public partial class Visitor : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
Pattern.Visitor.Messages m = new Pattern.Visitor.Messages();
m.Attach(new SqlMessage(new MessageModel("插入", DateTime.Now)));
m.Attach(new XmlMessage(new MessageModel("插入", DateTime.Now)));
Response.Write(m.Accept(new InsertVisitor()));
Response.Write(m.Accept(new GetVisitor()));
}
}
運行結果
True
True
SQL方式獲取Message 2007-5-27 15:01:53
XML方式獲取Message 2007-5-27 15:01:53
參考
http://www.dofactory.com/Patterns/PatternVisitor.aspx
OKa