编程中无法回避的基础知识---事务

来源:互联网 发布:行知职高有哪些专业 编辑:程序博客网 时间:2024/04/29 06:28


编程中无法回避的基础知识---事务

        


         进行软件开发已经有一段时间了,有些东西虽然一直在用但是并不是很理解为什么去用它,它的机制又是什么,是不是还有其他的用途?就像我们在对数据库进行一系列操作时,我们为了保证数据的一致性往往会用到事务。本文将简单的介绍一下事务的相关知识,和简单用法。

 

         基本概念

 

         定义

         事务是将一系列 数据源更新分组或分批的方法,以便在回滚事务时同时提交所有事务或者不提交任何事务[MSDN]。

         事务(Transaction)是访问并可能更新数据库中各种数据项的一个程序执行单元(unit)。事务通常由高级数据库操纵语言或编程语言(如SQL,C++或Java)书写的用户程序的执行所引起,并用形如begintransaction和end transaction语句(或函数调用)来界定。事务由事务开始(begintransaction)和事务结束(end transaction)之间执行的全体操作组成。[百度百科]

         特性

         事务是恢复和并发控制的基本单位。具有4个属性:原子性(Atomicity)、一致性(Consistency)、隔离性(Isolation)、持久性(Durability)。

         类型

         按事务是否跨越多数据资源来分类:

         1)本地事务:事务操作一个数据资源,如数据库和消息队列。在物理上表现为位于同一台计算机。

         2)分布事务:事务跨越多个数据源,如操作两个服务器上的数据库。

         按事务处理方式划分:

         1)手动事务:使用显示指令来控制事务的开始和结束,这种方式可以处理嵌套事务。SQLServer,ADO.NET都提供手动事务处理。

         2)自动事务:通过有组件声明事务特性,把组件自动置于事务环境中。使用自动事务不能处理嵌套事务。自动事务的本质是依托于COM+。

 

         简单的实例


         实例一

namespace 简单的事务{    class Program    {        private static  Test test;        static void Main(string[] args)        {            test=new Test();            test.Add();                   }    }     public class Test    {        SqlConnection conn = new SqlConnection("datasource=.;Initial Catalog=Test;Integrated Security=SSPI;Persist SecurityInfo=False");        public void Add()        {            conn.Open();            SqlCommand command = new SqlCommand("insert intotest2 values(111)", conn);            try            {                command.Transaction =conn.BeginTransaction();                command.ExecuteNonQuery();                command.CommandText = "insert intotest values(222)";                command.ExecuteNonQuery();                command.Transaction.Commit();            }            catch (Exception err)            {                Console.WriteLine(err);                Console.ReadKey();                command.Transaction.Rollback();            }        }    } }

 

         实例二

         这是一个简单三层的事务示例,

namespace 事务    //U层的代码{    class Program    {               static void Main(string[] args)        {            bll sbll = new bll();            bool flag =sbll.MoveScore();            if (flag == true)            {                Console.WriteLine("事务执行成功");            }            else            {                Console.WriteLine("事务执行失败");            }        }    }} namespace AddTestBll   //BLL层{    public class bll    {         private dal dal;          public Boolean MoveScore() {             SqlConnection sqlCon = new SqlConnection("datasource=.;Initial Catalog=Test;Integrated Security=SSPI;Persist SecurityInfo=False");        //打开连接       sqlCon.Open() ;            //定义事务        SqlTransaction sqlTran =sqlCon.BeginTransaction(IsolationLevel.ReadCommitted);            //用try...Catch...finally保证事务在出错时会回滚            try            {                int intResult =dal.Add1(sqlTran);                int intResult1 =dal.add2(sqlTran);                 if (1 == intResult&& 1 == intResult1)                {                    //如果都为真,提交                    sqlTran.Commit();                    return true;  //添加成功                }                else                {                    sqlTran.Rollback();                    return false; //添加失败                }                            }            catch (Exception e)            {                //出现异常时,事物回滚                sqlTran.Rollback();                return false;            }             finally            {                sqlCon.Close();            }                   }    }         } namespace AddTestDal      //Dal层{    public class dal    {        test enTest = new test();        private SQLHelper sqlHelper;        public int Add1(SqlTransaction sqlTran)        {            int intResult = 0;            //enTest.Id ="222";            string strSql = "insert intotest values(222)";            intResult =sqlHelper.ExecuteNonQuery(strSql, CommandType.Text, sqlTran);             return intResult;        }         public int add2(SqlTransaction sqlTran)        {            int intResult = 0;            string strSql = "insert intotest values(111)";            intResult =sqlHelper.ExecuteNonQuery(strSql, CommandType.Text, sqlTran);            return intResult;        }    }    public class SQLHelper    {        private SqlConnection conn = null;        private SqlCommand cmd = null;        private SqlDataReader sdr = null;         public SQLHelper()        {            string connStr = "datasource=.;Initial Catalog=Test;Integrated Security=SSPI";            conn = new SqlConnection(connStr);        }         private SqlConnection GetConn()        {            if (conn.State == ConnectionState.Closed)            {                conn.Open();            }            return conn;        }        ///<summary>        ///执行带参数的增删改SQL语句或存储过程        ///</summary>        ///<paramname="cmdText">增删改SQL语句或存储过程</param>        ///<paramname="paras">参数集合</param>        ///<paramname="cType">命令类型</param>        ///<returns>返回更新的记录条数</returns>        public int ExecuteNonQuery(string cmdText, CommandType cType, SqlTransaction sqlTran)        {            try            {                //实例化数据库命令SqlCommand                cmd = new SqlCommand(cmdText,GetConn());                //命令类型:存储过程or SQL语句                cmd.CommandType = cType;                cmd.CommandTimeout = 180; //设置最大连接时间                //事务                cmd.Transaction = sqlTran;                //定义事务执行结果                int intResult =cmd.ExecuteNonQuery();                //执行事务:大于0返回true,否则返回false。                if (intResult > 0)                {                    //事务执行成功                    return intResult;                }                else                {                    //事务执行失败                    return intResult;                }            }            catch (Exception ex)            {                //抛出异常                throw ex;            }        }    }}

      

         上面是两个关于本地事务的小例子,最近项目中用到了分布式而底层还用到了EF,这样就要求运用到分布式事务了,研究中,如果读者有相关的资料希望能分享给大家,谢谢!

         文中代码自建了一个测试库里面两张表的表结构如下(记得设置主键)

        

 

         优秀的博客推荐:

         1、.NET简谈事务、分布式事务处理:http://wangqingpei557.blog.51cto.com/1009349/748799/

         2、简述.net中有哪几种事务:http://wangzhiyu110.blog.sohu.com/156427139.html

         3、.NET简谈事务本质论:http://wangqingpei557.blog.51cto.com/1009349/719056

3 0
原创粉丝点击