今天早晨起来看到了好友
jyk 的
Step By Step 一步一步写网站 系列文章,感觉自己是时候兑现一下
之前的承诺 了,于是把这篇《关于数据访问》作为《轻松打造个人网站》系列文章的开篇,希望对各位有意架设个人网站的朋友有所帮助。我的水平有限,所以仅仅希望把自己在网站建设中的一些实战过程分享给大家,都是一家之谈,仅供各位参考。
长篇大论之前先展示一下我的网站吧。
活在沈阳:
http://www.024so.com/ 网站仍然处于测试调整阶段,欢迎各位原有访问,指正。最近仿佛不只一次在园子里提到我的网站了,呵呵。已经为流量开始不择手段了。
先说说项目情况吧,asp.net 2.0技术,工期从春节放假前2月15日到315消费者权益日,整一个月,期间包括网站功能设计,页面绘制,代码编写,注册域名,联系网络空间...酸甜苦辣各种滋味尽在其中。
罗嗦了半天,终于开始进入正题-“数据访问”了。大家都知道一般网站项目,从建立连接开始,到对数据操作或者返回结果集,关闭连接,整个过程中,最消耗时间不是对数据操作的过程,而是连接对象创建的过程,所以无论是.net阵营IIS服务器,或者java阵营Tom Cat都在自己web服务器中加入了连接池的概念,以减少连接对象创建和销毁过程中的消耗。如果你自己有一服务器,那么一切都没问题,连接池有多少触点你说了算,只需要手动配置一下连接字符串就ok了,像我这样比较穷酸的,只能租个廉价网络空间,而代理空间往往会限制IIS连接数量,所以为了提高网站访问速度,程序中对连接对象的控制就显得尤为重要。
举例说明吧,一个门户网站首页,一定有很多信息列表,比如有10个信息列表,是不是做了“创建10个连接,查询数据,把数据装入结果集,关闭连接,把结果集在前台送显”的过程呢?不是。拿我的网站来说,IIS限制50连接,就是说同一时间允许50个连接对象创建,假设一个页面显示需要5个查询的过程,那我就只能祈祷同一时刻不要有第11个人访问我的网站,事实上我希望同一时刻有1万个用户访问我的网站,呵呵。例子有点极端,我的态度也有些夸张。于是开发人员想出了许多解决方案,比如缓存结果集,比如静态页技术,比如流操作技术,比如一连接返回所有结果集技术......
对于我的网络空间实际情况,我采取了一连接技术和缓存结果集技术。详细讲:
直接看代码吧:

// 初始化首页显示信息#region // 初始化首页显示信息

/**//// <summary>
/// 初始化首页显示信息
/// <param name="topicList">首页文章列表</param>
/// <param name="topicCount">首页文章列表数量</param>
/// <param name="userList">最新用户列表</param>
/// <param name="userCount">最新用户数量</param>
/// </summary>
public void GetIndexData(
out IList<TopicInfo> topicList, out IList<UserDetailInfo> userList,
int topicCount, int userCount)

{
IList<TopicInfo> tList = null;
IList<UserDetailInfo> uList = null;
try

{
using (SqlConnection conn = new SqlConnection(connString))

{
conn.Open();
SqlCommand cmd = new SqlCommand();
cmd.Connection = conn;
cmd.CommandType = CommandType.StoredProcedure;


// 获得首页文章列表#region // 获得首页文章列表
cmd.CommandText = "ayuan_topic_topfordescription";
cmd.Parameters.Add("@count", SqlDbType.Int, 4);
cmd.Parameters[0].Value = topicCount;
using (IDataReader reader = cmd.ExecuteReader())

{
// TopicID, UseriD, GroupID, Title, Description, PubDate,
// Rc, Pv, Tag, NickName, Figure, GroupTitle, UserDesc
tList = new List<TopicInfo>();
while (reader.Read())

{
TopicInfo info = new TopicInfo();
info.TopicID = reader.GetInt32(0);
info.UserID = reader.GetInt32(1);
info.GroupID = reader.GetInt32(2);
info.Title = reader.GetString(3);
info.Description = reader.GetString(4);
info.PubDate = reader.GetDateTime(5);
info.Rc = reader.GetInt32(6);
info.Pv = reader.GetInt32(7);
info.Tag = (reader[8] is DBNull) ? string.Empty : reader.GetString(8);
info.NickName = reader.GetString(9);
info.Figure = reader.GetString(10);
info.GroupTitle = reader.GetString(11);
info.UserDescription = reader.GetString(12);
tList.Add(info);
}
}
cmd.Parameters.Clear();
#endregion

// 获得最新注册用户列表#region // 获得最新注册用户列表
cmd.CommandText = "ayuan_view_userinfo_top";
cmd.Parameters.Add("@count", SqlDbType.Int, 4);
cmd.Parameters[0].Value = userCount;
using (IDataReader reader = cmd.ExecuteReader())

{
// UserID, NickName, Figure
uList = new List<UserDetailInfo>();
while (reader.Read())

{
UserDetailInfo info = new UserDetailInfo();

info.UserID = reader.GetInt32(0);
info.NickName = reader.GetString(1);
info.Figure = reader.GetString(2);

uList.Add(info);
}
}
cmd.Parameters.Clear();
#endregion
}
}
catch(Exception ex)

{
throw ex;
}
topicList = tList;
userList = uList;
}
#endregion
大家看到了,这个方法用于返回首页用于显示的多个集合列表,是的,用一个方法返回多个结果集:
public void GetIndexData(
out IList<TopicInfo> topicList, out IList<UserDetailInfo> userList,
int topicCount, int userCount)
这里用到了输出参数,方法中包含多个数据访问的过程,这些查询过程公用了一个Connection对象,把Connection对象放在Using操作空间中,限制了Connection的工作空间,保证所有数据访问结束之后Connection对象自动析构。还要注意的是Command对象,很多查询都是带参操作的,所以当一个数据访问结束之后一定要清空Command对象的参数:
cmd.Parameters.Clear();
这样就实现了一连接返回多个查询结果集。有些朋友可能会说这样的数据访问,代码量会不会比较大。
的确会,不过其中的代码都比较规律,都是最纯朴的ado.net,所以老刘推荐使用诸如CodeSmith之类的代码生成工具写出模版,成批生成代码。
还有不同页面显示相同的数据访问内容的情况,那么就会在多个方法中包含相同的数据访问部分,老刘的网站里没有多个页面显示相同内容的情况,所以用了上面的方法,如果你的项目里有多页通用结果集,那么老刘推荐你重构一下上面的方法,把数据访问部分提炼成方法,然后把Connection对象作为参数在方法中传递,或者你也可以把第一次查询出来的结果放到缓存中,其他页面调用缓存中的数据,不过自己要控制好这个过程,比较复杂,在此不详细叙述,关于缓存数据,我会结合我的项目实际情况,作为专题叙述一下。提到缓存不能不介绍一篇好文,偶像Bruce Zhang的PetShop之ASP.NET缓存,这里仿佛应该引用韦小宝的滔滔江水之云云,呵呵。
以上文字只代表了我不成熟的观点,如果能给你带来一丝灵感,老刘会感到非常开心,第一次把文章放在首页,欢迎各位园友拍砖。还会写几篇《轻松打造个人网站》系列的文章,也许不只包括技术方面的,还包括一些运营,推广方面的实践经验,衷心希望给各位有意打造个人网站的朋友带来帮主,因为我切身体会了其中的艰辛,呵呵。
对所有提出指正的朋友表示衷心感谢:)
============================================
引自 亚历山大同志
@老刘.
----------------------------------------------------------------
像我这样比较穷酸的,只能租个廉价网络空间,而代理空间往往会限制IIS连接数量,所以为了提高网站访问速度,程序中对连接对象的控制就显得尤为重要
----------------------------------------------------------------
这里需要纠正一下你的观点,可能对服务器配置你是不是很熟悉.所谓IIS连接数是指IIS同时能够处理的浏览器请求的数量,而不是服务器去连接数据库的连接的数量,我想你这点完全理解错误了,对于Access数据库来说数据连接数量毫无意义,本来就是文件型的数据库而SqlServer是要设置的一般来说很多虚拟主机商都会做出一定的限制,而IIS的连接数限制不管你的程序怎么优化怎么单连接阿什么的都是没有用的,因为那是IIS的地盘,超过同时请求的用户数IIS请求都不会转发给ASP.NET.我看你的基本出发点都弄错了.
============================================