首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >深入浅出三层架构

深入浅出三层架构

作者头像
用户1161731
发布2018-01-11 12:12:23
9740
发布2018-01-11 12:12:23
举报
文章被收录于专栏:木宛城主木宛城主

这几天看了不少三层架构的资料,整理整理

——故写篇博文谈谈自己的看法。

三层架构概念:

三层架构(3-tier application) 通常意义上的三层架构就是将整个业务应用划分为:表现层(UI)、业务逻辑层(BLL)、数据访问层(DAL)。区分层次的目的即为了“高内聚,低耦合”的思想,复杂项目不能把SQL语句直接写到程序里,不模块话,难以维护。应该采取三层架构。

1、表现层(UI):通俗讲就是展现给用户的界面,即用户在使用一个系统的时候他的所见所得。

2、业务逻辑层(BLL):针对具体问题的操作,也可以说是对数据层的操作,对数据业务逻辑处理。

3、数据访问层(DAL):该层所做事务直接操作数据库,针对数据的增添、删除、修改、查找等。

简单的说,UI层调用BLL,BLL调用DAL,数据用Model进行传递,Model为各层之间架起了数据传输的桥梁。

参考模型:UI<-->Model<-->BLL<-->Model<-->DAL

传统的两层结构和三层架构之间的区别:

下面我以一个简单的例子来细数三层架构:

代码剖析:

  • 新建一个项目(Windows 窗体应用程序),再在根目录下新建3个文件夹,分别是Model,DAL,BLL。
  • 在Model下添加一个Person类
  • 在DAL下添加一个SQLHelper类和一个PersonDAL类。
  • 在BLL下添加PersonBLL类

Person.cs代码如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace 三层架构Demo.Model
{
    class Person
    {
        public int Id { get;set;}
        public int Age { get; set; }
        public string Name { get; set; }

    }
}

SQLHelper类,封装了数据库操作的方法:

SQLHelper.cs代码入下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Data.SqlClient;
using System.Configuration;
using System.Data;

namespace 三层架构Demo.DAL
{
    class SQLHelper
    {
        //public static readonly string connStr = System.Configuration.ConfigurationSettings.AppSettings["dbconnstr"];
        //获得连接字符串
        public static readonly string connStr =
            ConfigurationManager.ConnectionStrings["dbconnstr"].ConnectionString;

        /// <summary>
        /// 执行方法ExecuteNonQuery
        /// </summary>
        /// <param name="cmdText">要执行的sql语句</param>
        /// <param name="parameters">参数数组</param>
        /// <returns>受影响的行数</returns>
        public static int ExecuteNonQuery(string cmdText,
            params SqlParameter[] parameters)
        {
            using (SqlConnection conn=new SqlConnection (connStr))
            {
                conn.Open();
                using (SqlCommand cmd= conn.CreateCommand())
                {
                    cmd.CommandText = cmdText;
                    cmd.Parameters.AddRange(parameters);
                    int i=cmd.ExecuteNonQuery();
                    return i;
                }
            }
        }

        /// <summary>
        /// 执行ExecuteScalar() 返回第一行第一列数据
        /// </summary>
        /// <param name="cmdText">要执行的sql语句</param>
        /// <param name="parameters">参数数组</param>
        /// <returns>返回第一行第一列数据</returns>
        public static  object ExecuteScalar(string cmdText,
            params SqlParameter[] parameters)
        {
            using (SqlConnection conn=new SqlConnection(connStr))
            {
                conn.Open();
                using (SqlCommand cmd=conn.CreateCommand())
                {
                    cmd.CommandText = cmdText;
                    cmd.Parameters.AddRange(parameters);
                    return cmd.ExecuteScalar();
                }
            }
        }

        /// <summary>
        /// 执行ExecuteDataTable()方法
        /// </summary>
        /// <param name="cmdText">要执行的Sql语句</param>
        /// <param name="parameters">参数数组</param>
        /// <returns>返回一个DataTable</returns>
        public static  DataTable ExecuteDataTable(string cmdText,
            params SqlParameter[] parameters)
        {
            using (SqlConnection conn=new SqlConnection (connStr))
            {
                conn.Open();
                using (SqlCommand cmd=conn.CreateCommand())
                {
                    cmd.CommandText = cmdText;
                    cmd.Parameters.AddRange(parameters);
                    using ( SqlDataAdapter adapter=new SqlDataAdapter (cmd))
                    {
                        DataTable dt = new DataTable();
                        adapter.Fill(dt);
                        return dt;
                    }
                }
            }
        }

       /// <summary>
        /// 执行ExecuteSqlDataReader()方法
       /// </summary>
       /// <param name="cmdText">要执行的Sql语句</param>
       /// <param name="parameters">参数数组</param>
        /// <returns>返回一个SqlDataReader</returns>

        public static SqlDataReader ExecuteSqlDataReader(string cmdText,
            params SqlParameter[] parameters)
        {
            using (SqlConnection conn=new SqlConnection (connStr))
            {
                conn.Open();
                using (SqlCommand cmd=conn.CreateCommand())
                {
                    cmd.CommandText = cmdText;
                    cmd.Parameters.AddRange(parameters);
                    return cmd.ExecuteReader();
                }
            }
        }                                                 
    }
}
复制代码

PersonDAL.cs代码如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using 三层架构Demo.Model;
using System.Data.SqlClient;
using System.Data;

namespace 三层架构Demo.DAL
{
    class PersonDAL
    {
        /// <summary>
        /// 返回一个新增对象的主键,设为自动增长
        /// </summary>
        /// <param name="model"></param>
        /// <returns></returns>
        public int Addnew(Person model)
        {
            string sql = "insert into T_person(Age,Name) output inserted.id values(@Age,@Name)";
         
            object obj=
                SQLHelper.ExecuteScalar(sql,new SqlParameter("Age",model.Age),new SqlParameter("Name",model.Name));
            //Convert : 与 value 等效的 32 位有符号整数,如果 value 为 null,则为零。
            return Convert.ToInt32(obj);
        }
        /// <summary>
        /// 删除数据
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public int Delete(int id)
        {
            string sql = "delete form T_Person where Id=@Id";
            return SQLHelper.ExecuteNonQuery(sql,new SqlParameter("Id",id));
        }
        /// <summary>
        /// 修改数据
        /// </summary>
        /// <param name="model"></param>
        /// <returns></returns>
        public int Update(Person model)
        {
            string sql = "update T_Person set Age=@Age,Name=@Name where Id=@Id";
            return SQLHelper.ExecuteNonQuery(sql,new SqlParameter("Age",model.Age),new SqlParameter("Name",model.Name),
                new SqlParameter("Id",model.Id));
        }

        /// <summary>
        /// 查询数据
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public Person Get(int id)
        {
            string sql="select * from T_Person where Id=@Id";
            DataTable dt=SQLHelper.ExecuteDataTable(sql,new SqlParameter("Id",id));
            if (dt.Rows.Count<=0)
            {
                return null;
            }
            else if (dt.Rows.Count==1)
            {
                Person model1 = new Person();
                model1.Id = Convert.ToInt32(dt.Rows[0]["Id"]);
                model1.Name = Convert.ToString(dt.Rows[0]["Name"]);
                model1.Age = Convert.ToInt32(dt.Rows[0]["Age"]);
                return model1;
            }
            else//以防意外情况
            {
                throw new Exception("数据库中有两条及以上重复数据");
            }
        }
        /// <summary>
        /// 获取全部数据
        /// </summary>
        /// <returns></returns>
        public IEnumerable<Person> GetAll()
        {
            string sql = "select * from T_Person";
            DataTable dt = SQLHelper.ExecuteDataTable(sql);
            List<Person> list = new List<Person>();
            foreach (DataRow row in dt.Rows)
            {
                Person model = new Person();
                model.Id = Convert.ToInt32(row["Id"]);
                model.Name =Convert.ToString(row["Name"]);
                model.Age = Convert.ToInt32(row["Age"]);
                list.Add(model);
            }
            return list;
        }
    }
}

进行逻辑判断的BLL层代码看似是这样的:

PersonBLL.cs代码如下:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using 三层架构Demo.Model;
using 三层架构Demo.DAL;
using System.Data.SqlClient;
using System.Data;

namespace 三层架构Demo.BLL
{
    class PersonBLL
    {
        public int Addnew(Person model)
        {
            return new PersonDAL().Addnew(model);
        }

        public int Delete(int id)
        {
            return new PersonDAL().Delete(id);
        }

        public int Update(Person model)
        {
            return new PersonDAL().Update(model);
        }

        public Person Get(int id)
        {
            return new PersonDAL().Get(id);
        }

        public IEnumerable<Person> GetAll()
        {
            return new PersonDAL().GetAll();
        }


    }
}

UI层进行测试:

Form1.cs代码如下:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using 三层架构Demo.Model;
using 三层架构Demo.DAL;
using 三层架构Demo.BLL;

namespace 三层架构Demo
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        private void button1_Click(object sender, EventArgs e)
        {
            //Person p1 = new Person();
            //p1.Age = 22;
            //p1.Name = "Eyes";
            //int id=new PersonDAL().Addnew(p1);
            //MessageBox.Show(id.ToString());

            //PersonDAL p = new PersonDAL();
            //Person a = p.Get(1);
            //a.Name = "jack";
            //MessageBox.Show(a.Name + "," + a.Age);
            //p.Update(a);


            //PersonBLL bll = new PersonBLL();
            //Person p = bll.Get(1);
            //p.Name = "Admin";
            //MessageBox.Show(p.Name + "," + p.Age);
            //bll.Update(p);

            PersonBLL b = new PersonBLL();
            List<Person> list = (List<Person>)b.GetAll();
            foreach (Person item in list)
            {
                MessageBox.Show(item.Id+","+item.Name+","+item.Age);
            }
            
        }

        private void Form1_Load(object sender, EventArgs e)
        {
            dataGridView1.DataSource = new PersonBLL().GetAll();
        }
    }
}
复制代码

总结:

优点

  1、开发人员可以只关注整个结构中的其中某一层;

  2、可以很容易的用新的实现来替换原有层次的实现;

  3、可以降低层与层之间的依赖;

  4、有利于标准化;

  5、利于各层逻辑的复用。

缺点

  1、降低了系统的性能。这是不言而喻的。如果不采用分层式结构,很多业务可以直接造访数据库,以此获取相应的数据,如今却必须通过中间层来完成。

  2、有时会导致级联的修改。这种修改尤其体现在自上而下的方向。如果在表示层中需要增加一个功能,为保证其设计符合分层式结构,可能需要在相应的业务逻辑层和数据访问层中都增加相应的代码。

  3、增加了开发成本。

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2012-02-10 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 三层架构概念:
    • 传统的两层结构和三层架构之间的区别:
    • 代码剖析:
      • Person.cs代码如下:
        • SQLHelper.cs代码入下:
          • PersonDAL.cs代码如下:
            • Form1.cs代码如下:
            • 总结:
              • 优点
                • 缺点
                相关产品与服务
                数据库
                云数据库为企业提供了完善的关系型数据库、非关系型数据库、分析型数据库和数据库生态工具。您可以通过产品选择和组合搭建,轻松实现高可靠、高可用性、高性能等数据库需求。云数据库服务也可大幅减少您的运维工作量,更专注于业务发展,让企业一站式享受数据上云及分布式架构的技术红利!
                领券
                问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档