我的个人网站上有一个页面,主要介绍了一些我喜欢的书籍,目前有9本,这样把页面拉的很长,挺影响美观的,于是决定分页显示它们。我没有SQL数据库,而且我也不想用复杂的数据库来存放这种简单的数据,所以我用的是XML文件,把它读入DataSet,然后再在Repeater中显示。
如果是SQL数据库或Access等,分页到是挺简单的,但是我存放数据的是XML文件,又不能用SQL语句,怎么办呢?问了一个高手,知道了还有一种叫XPath的语言,又学到一些东西了,不敢偷懒,马上记下。
//首先尝试从缓存中读取
XmlDataDocument doc = SiteCache.Get("Doc") as XmlDataDocument;
DataSet ds = SiteCache.Get("Books") as DataSet;
if(doc == null && ds == null) {
string path;
if(HttpContext.Current != null)
path = HttpContext.Current.Server.MapPath("~/Content/Books.xml");
else
path = Directory.GetCurrentDirectory() + Path.DirectorySeparatorChar + "Content/Books.xml";
ds = new DataSet();
ds.ReadXml(path);
doc = new XmlDataDocument(ds);
SiteCache.Max("Doc", doc, new System.Web.Caching.CacheDependency(path));
SiteCache.Max("Books", ds, new System.Web.Caching.CacheDependency(path));
}
//总数据项为DataRow的个数
pager.TotalRecords = ds.Tables[0].Rows.Count;
int current = pager.PageIndex * pager.PageSize;
int target = current + pager.PageSize;
string xpath = String.Format("/Books/Book[position()>{0} and position()<={1}]", current, target);
XmlNodeList nodes = doc.DocumentElement.SelectNodes(xpath);
DataRow row = null;
DataSet ds2 = ds.Clone();
ds2.Clear();
foreach(XmlNode node in nodes) {
row = doc.GetRowFromElement((XmlElement)node);
//ds2.Tables[0].Rows.Add(row); 不能用这样的语句,否则会抛异常
ds2.Tables[0].ImportRow(row);
}
books.DataSource = ds2;
books.DataBind();
XmlDataDocument doc = SiteCache.Get("Doc") as XmlDataDocument;
DataSet ds = SiteCache.Get("Books") as DataSet;
if(doc == null && ds == null) {
string path;
if(HttpContext.Current != null)
path = HttpContext.Current.Server.MapPath("~/Content/Books.xml");
else
path = Directory.GetCurrentDirectory() + Path.DirectorySeparatorChar + "Content/Books.xml";
ds = new DataSet();
ds.ReadXml(path);
doc = new XmlDataDocument(ds);
SiteCache.Max("Doc", doc, new System.Web.Caching.CacheDependency(path));
SiteCache.Max("Books", ds, new System.Web.Caching.CacheDependency(path));
}
//总数据项为DataRow的个数
pager.TotalRecords = ds.Tables[0].Rows.Count;
int current = pager.PageIndex * pager.PageSize;
int target = current + pager.PageSize;
string xpath = String.Format("/Books/Book[position()>{0} and position()<={1}]", current, target);
XmlNodeList nodes = doc.DocumentElement.SelectNodes(xpath);
DataRow row = null;
DataSet ds2 = ds.Clone();
ds2.Clear();
foreach(XmlNode node in nodes) {
row = doc.GetRowFromElement((XmlElement)node);
//ds2.Tables[0].Rows.Add(row); 不能用这样的语句,否则会抛异常
ds2.Tables[0].ImportRow(row);
}
books.DataSource = ds2;
books.DataBind();
上面的代码中,pager是一个分页控件,books是一个Repeater,用XPath选择要读取的节点,把它赋值到一个DataRow中,然后将之导入DataTable中,再绑定到Repeater上,就可以显示了。这里遇到个小问题,不能用ds2.Tables[0].Rows.Add(row);这个语句,否则会抛个“此DataRow已属于另一个DataTable”的异常,不知为什么,改为ImportRow就没问题了。希望哪位高手知道,请告诉我一声,谢谢。