- 浏览: 500019 次
- 性别:
- 来自: 深圳
文章分类
最新评论
-
michao:
大哥,还有aperture.exe吗? 发我一份,找不到呀,m ...
使用aperture框架让AS3与C++通信,执行本地代码 -
Aaron-Joe-William:
文件被删除了。下不了。
SQLite 数据库加密的一种解决方案 -
hanmiao:
樓主的文章不就是來自IBM Developers里的http: ...
mina 入门 -
howesen:
断包与粘包问题,需要处理下就好了
mina接收数据不全(2) -
sniciq:
git clone --recursive git://git ...
ESB学习笔记(Spring Integration实战)
-
本文讨论如何在C#中实现三层架构,使用MS Access数据库存储数据。同时在三层架构中实现一个小型的可复用的组件来保存客户数据,并提供添加、更新、查找客户数据的功能。
这篇文章讨论如何在C#中实现三层架构,使用MS Access数据库存储数据。在此,我在3层架构中实现一个小型的可复用的组件保存客户数据。并提供添加,更新,查找客户数据的功能。
背景
首先,我介绍一些3层架构的理论知识。简单说明:什么是3层架构?3层架构的优点是什么?
什么是三层架构?
3层架构是一种“客户端-服务器”架构,在此架构中用户接口,商业逻辑,数据保存以及数据访问被设计为独立的模块。主要有3个层面,第一层(表现层,GUI层),第二层(商业对象,商业逻辑层),第三层(数据访问层)。这些层可以单独开发,单独测试。
为什么要把程序代码分为3层。把用户接口层,商业逻辑层,数据访问层分离有许多的优点。
在快速开发中重用商业逻辑组件,我们已经在系统中实现添加,更新,删除,查找客户数据的组件。这个组件已经开发并且测试通过,我们可以在其他要保存客户数据的项目中使用这个组件。
系统比较容易迁移,商业逻辑层与数据访问层是分离的,修改数据访问层不会影响到商业逻辑层。系统如果从用SQL Server存储数据迁移到用Oracle存储数据,并不需要修改商业逻辑层组件和GUI组件
系统容易修改,假如在商业层有一个小小的修改,我们不需要在用户的机器上重装整个系统。我们只需要更新商业逻辑组件就可以了。
应用程序开发人员可以并行,独立的开发单独的层。
代码
这 个组件有3层,第一个层或者称为GUI层用form实现,叫做FrmGUI。第二层或者称为商业逻辑层,叫做BOCustomer,是Bussniess Object Customer的缩写。最后是第三层或者称为数据层,叫做DACustomer,是Data Access Customer的缩写。为了方便,我把三个层编译到一个项目中。
用户接口层
下面是用户接口成的一段代码,我只选取了调用商业逻辑层的一部分代码。
//This function get the details from the user via GUI //tier and calls the Add method of business logic layer. private void cmdAdd_Click(object sender, System.EventArgs e) { try { cus = new BOCustomer(); cus.cusID=txtID.Text.ToString(); cus.LName = txtLName.Text.ToString(); cus.FName = txtFName.Text.ToString(); cus.Tel= txtTel.Text.ToString(); cus.Address = txtAddress.Text.ToString(); cus.Add(); } catch(Exception err) { MessageBox.Show(err.Message.ToString()); } } //This function gets the ID from the user and finds the //customer details and return the details in the form of //a dataset via busniss object layer. Then it loops through //the content of the dataset and fills the controls. private void cmdFind_Click(object sender, System.EventArgs e) { try { String cusID = txtID.Text.ToString(); BOCustomer thisCus = new BOCustomer(); DataSet ds = thisCus.Find(cusID); DataRow row; row = ds.Tables[0].Rows[0]; //via looping foreach(DataRow rows in ds.Tables[0].Rows ) { txtFName.Text = rows["CUS_F_NAME"].ToString(); txtLName.Text = rows["CUS_L_NAME"].ToString(); txtAddress.Text = rows["CUS_ADDRESS"].ToString(); txtTel.Text = rows["CUS_TEL"].ToString(); } } catch (Exception err) { MessageBox.Show(err.Message.ToString()); } } //this function used to update the customer details. private void cmdUpdate_Click(object sender, System.EventArgs e) { try { cus = new BOCustomer(); cus.cusID=txtID.Text.ToString(); cus.LName = txtLName.Text.ToString(); cus.FName = txtFName.Text.ToString(); cus.Tel= txtTel.Text.ToString(); cus.Address = txtAddress.Text.ToString(); cus.Update(); } catch(Exception err) { MessageBox.Show(err.Message.ToString()); } }
商业逻辑层
下面是商业逻辑层的所有代码,主要包括定义customer对象的属性。但这仅仅是个虚构的customer对象,如果需要可以加入其他的属性。商业逻辑层还包括添加,更新,查找,等方法。
商业逻辑层是一个中间层,处于GUI层和数据访问层中间。他有一个指向数据访问层的引用cusData = new DACustomer().而且还引用了System.Data名字空间。商业逻辑层使用DataSet返回数据给GUI层。
using System;
using System.Data;
namespace _3tierarchitecture
{
///
/// Summary description for BOCustomer.
///
public class BOCustomer
{
//Customer properties
private String fName;
private String lName;
private String cusId;
private String address;
private String tel;
private DACustomer cusData;
public BOCustomer()
{
//An instance of the Data access layer!
cusData = new DACustomer();
}
///
/// Property FirstName (String)
///
public String FName
{
get
{
return this.fName;
}
set
{
try
{
this.fName = value;
if (this.fName == "")
{
throw new Exception(
"Please provide first name ...");
}
}
catch(Exception e)
{
throw new Exception(e.Message.ToString());
}
}
}
///
/// Property LastName (String)
///
public String LName
{
get
{
return this.lName;
}
set
{
//could be more checkings here eg revmove ' chars
//change to proper case
//blah blah
this.lName = value;
if (this.LName == "")
{
throw new Exception("Please provide name ...");
}
}
}
///
/// Property Customer ID (String)
///
public String cusID
{
get
{
return this.cusId;
}
set
{
this.cusId = value;
if (this.cusID == "")
{
throw new Exception("Please provide ID ...");
}
}
}
///
/// Property Address (String)
///
public String Address
{
get
{
return this.address;
}
set
{
this.address = value;
if (this.Address == "")
{
throw new Exception("Please provide address ...");
}
}
}
///
/// Property Telephone (String)
///
public String Tel
{
get
{
return this.tel;
}
set
{
this.tel = value;
if (this.Tel == "")
{
throw new Exception("Please provide Tel ...");
}
}
}
///
/// Function Add new customer. Calls
/// the function in Data layer.
///
public void Add()
{
cusData.Add(this);
}
///
/// Function Update customer details.
/// Calls the function in Data layer.
///
public void Update()
{
cusData.Update(this);
}
///
/// Function Find customer. Calls the
/// function in Data layer.
/// It returns the details of the customer using
/// customer ID via a Dataset to GUI tier.
///
public DataSet Find(String str)
{
if (str == "")
throw new Exception("Please provide ID to search");
DataSet data = null;
data = cusData.Find(str);
return data;
}
}
}
数据访问层
数据层包括处理MS Access数据库的细节。所有这些细节都是透明的,不会影响到商业逻辑层。数据访问层有个指向商业逻辑层的引用BOCustomer cus。为了应用方便并且支持其他数据库。
using System;
using System.Data.OleDb;
using System.Data;
namespace _3tierarchitecture
{
///
/// Summary description for DACustomer.
///
public class DACustomer
{
private OleDbConnection cnn;
//change connection string as per the
//folder you unzip the files
private const string CnnStr =
"Provider=Microsoft.Jet.OLEDB.4.0;Data " +
"Source= D:\\Rahman_Backup\\Programming\\" +
"Csharp\\3tierarchitecture\\customer.mdb;";
//local variables
private String strTable="";
private String strFields="";
private String strValues="";
private String insertStr="";
//this needs to be changed based on customer
//table fields' Name of the database!
private const String thisTable = "tblCustomer";
private const String cus_ID = "CUS_ID";
private const String cus_LName = "CUS_L_NAME";
private const String cus_FName = "CUS_F_NAME";
private const String cus_Tel = "CUS_TEL";
private const String cus_Address = "CUS_ADDRESS";
public DACustomer()
{
}
public DACustomer(BOCustomer cus)
{
// A reference of the business object class
}
//standard dataset function that adds a new customer
public void Add(BOCustomer cus)
{
String str = BuildAddString(cus);
OpenCnn();
//Open command option - cnn parameter is imporant
OleDbCommand cmd = new OleDbCommand(str,cnn);
//execute connection
cmd.ExecuteNonQuery();
// close connection
CloseCnn();
}
//standard dataset function that updates
//details of a customer based on ID
public void Update(BOCustomer cus)
{
OpenCnn();
String selectStr = "UPDATE " + thisTable +
" set " + cus_LName + " = '" + cus.LName + "'" +
", " + cus_FName + " = '" + cus.FName + "'" +
", " + cus_Address + " = '" + cus.Address + "'" +
", " + cus_Tel + " = '" + cus.Tel + "'" +
" where cus_ID = '" + cus.cusID + "'";
OleDbCommand cmd = new OleDbCommand(selectStr,cnn);
cmd.ExecuteNonQuery();
CloseCnn();
}
//standard dataset function that finds and
//return the detail of a customer in a dataset
public DataSet Find(String argStr)
{
DataSet ds=null;
try
{
OpenCnn();
String selectStr = "select * from " + thisTable +
" where cus_ID = '" + argStr + "'";
OleDbDataAdapter da =
new OleDbDataAdapter(selectStr,cnn);
ds = new DataSet();
da.Fill(ds,thisTable);
CloseCnn();
}
catch(Exception e)
{
String Str = e.Message;
}
return ds;
}
private void OpenCnn()
{
// initialise connection
String cnnStr = CnnStr;
cnn = new OleDbConnection(cnnStr);
// open connection
cnn.Open();
}
private void CloseCnn()
{
// 5- step five
cnn.Close();
}
// just a supporting function that builds
// and return the insert string for dataset.
private String BuildAddString(BOCustomer cus)
{
// these are the constants as
// set in the top of this module.
strTable="Insert into " + thisTable;
strFields=" (" + cus_ID +
"," + cus_LName +
"," + cus_FName +
"," + cus_Address +
"," + cus_Tel + ")";
//these are the attributes of the
//customer business object.
strValues= " Values ( '" + cus.cusID +
"' , '" + cus.LName +
"' , '" + cus.FName +
"' , '" + cus.Address +
"' , '" + cus.Tel + "' )";
insertStr = strTable + strFields + strValues;
return insertStr;
}
}
}
发表评论
-
RichTextBox 添加控件,被禁用如何处理 button
2010-11-01 18:45 1255WPF中RichTextBox的确非 ... -
归纳一下:C#线程同步的几种方法
2010-10-28 11:18 1285我们在编程的时候,有时会使用多线程来解决问题, ... -
关于WPF ListView数据绑定 入门 及分类,排序
2010-09-03 18:14 9284不多说,先直接上代码 ... -
关于WPF 数据绑定简单介绍及入门
2010-09-02 20:07 5320今天搞了一下午的数据绑定,由于以前用FLEX的数据绑定很 ... -
何为插件化系统,插件化系统有何优势
2010-08-10 14:28 2308当一个软件项目开 ... -
回调函数原理
2010-08-10 12:04 2180回调函数原理 声明CALLBACK 调用(call ... -
C#制作屏幕保护的方法 函数
2010-08-10 10:16 1432本文介绍使用C#制作屏 ... -
初探C# 异常处理
2010-08-03 10:39 1295一、基础 在C# 里,异 ... -
C#中使用try catch对系统性能的影响和处理机制的学习总结!
2010-08-03 10:31 2805问题1:当一段代码被try ... -
C# WebClient上传下载时进度条显示,找了好久才找到的哦!
2010-07-23 11:05 76452、代码: using System; using Sys ... -
WinFrom通过WebClient上传下载文件(带进度条)
2010-07-23 10:48 4254(2009-09-27 12:18:09) 转 ... -
关于图片保存问题
2010-07-15 20:01 967如果你在用PngBitmapEncoder之类的 Save图片 ... -
Windows 7 任务栏开发 之 进度条(Progress Bar)
2010-07-12 14:33 1894上一篇 我们完成了“覆盖图标”(Overlay ... -
WPF 新弹出窗口抢焦点问题
2010-06-21 16:34 4057新弹出窗口抢了正在使用的窗口焦点,这个问题烦了好久,今天终于有 ... -
C# 第三方控件
2010-06-08 10:29 2978DevExpress,NetAdvantage 这两套算是最全 ... -
数据绑定
2010-05-31 18:42 806http://liutiemeng.blog.51cto.co ... -
C# 修改警告心得
2010-05-22 17:08 13861.(CA1031)如果有try catch最好不要捕获Exc ... -
C# log4net
2010-05-17 13:40 2149说明:本程序演示如何利用log4net记录程序日志信息。log ... -
C# 开机启动
2010-05-13 17:41 1622C# winform程序设置开机 ... -
Base64编码的字符串与图片的转换 C#
2010-04-28 15:05 2805using System; using System.Col ...
相关推荐
浅析C#编程中的内存管理浅析C#编程中的内存管理
浅析C#中object_sender与EventArgs_e
浅析C#中的文件操作 个人学习参考之用 与大家分享
浅析C#委托和事件实例 当第一次听到委托、事件时感觉比较抽象、很好奇,当看到老师在课堂上利用委托和事件实现两个窗体调用时、感觉委托太神奇了,呵、不废话了…… C#委托和事件在做程序是很常见到的,对于像我...
像Java一样,C#提供了一整套相当丰富的类库、方法以及事件以供开发者使用。C#还引入了GDI+,它是由GDI演变而来的,具有比GDI更强大的功能而且...本文,笔者就通过一些实例像读者介绍一下C#中的图形编程的基本知识。
了解C#中的预定义事件处理机制 在写代码前我们先来熟悉.net框架中和事件有关的类和委托,了解C#中预定义事件的处理。 EventArgs是包含事件数据的类的基类,用于传递事件的细节。 EventHandler是一个委托声明如下 ...
浅析C#中的套接字编程.docx,文章,不错
在写代码前我们先来熟悉.net框架中和事件有关的类和委托,了解C#中预定义事件的处理。 EventArgs是包含事件数据的基类,用于传递事件的细节。 EventHandler是一个委托声明如下 public delegate void EventHandler...
本文浅析了windows和C#的内存管理的机制,介绍了基本的内存管理方法
三层体系结构,即用户层、应用层和数据库服务器。用户层主要指用户界面,它要求尽可能的简单,使最终用户不需要进行任何培训就能方便地访问信息;第二层就是应用服务器,也就是常说的中间件,所有的应用系统、应用...
浅析SOA三层体系结构及发展状况.pdf浅析SOA三层体系结构及发展状况.pdf
主要介绍了C# 状态机Stateless的的相关资料,文中讲解非常详细,代码帮助大家更好的理解和学习,感兴趣的朋友可以了解下
引用了一个网站的内容,相当的给力,几个小例子非常适合初学者学习.
C#提供了一整套相当丰富的类库、方法以及事件以供开发者使用。C#还引入了GDI+,它是由GDI演变而来的,具有比GDI更强大的功能而且简化了程序员...本文,笔者就通过一些实例像读者介绍一下C#中的图形编程的基本知识。
实践论认为:从实践提升到理论,再由...当前国内要发展SOA主要有三方面工作:方法、工具和环境。方法是工程技术,由基础理论来指导提出的。所以一门科学必需要包括:认知科学(哲理)、工程技术和方法、最后是理论。
浅析路由器与三层交换机的异同及在消防网络中的应用.pdf
C#异步调用: .NET Framework 允许您C#异步调用任何方法。定义与您需要调用的方法具有相同签名的委托;公共语言运行库将自动为该委托定义具有适当签名的 BeginInvoke 和 EndInvoke 方法。
介绍三层架构,用三层架构的思想去设计网页