在数据库开发中,事务处理是非常重要的。

首先Android数据库操作(特别是写操作)是非常慢的,将所有操作打包成一个事务能大大提高处理速度。

其次是保证数据的一致性,一个事务中的所有操作可以看作一个原子操作,成功或者失败。如果全部成功,则事务提交完成;而事务内部如果有失败操作,整个事务操作会回滚,从而保证数据的一致性。

Android中事务的调用:

try {
	db.beginTransaction();
      	//在这里执行多个数据库操作
      	//执行过程中可能会抛出异常
        	db.setTransactionSuccessful();
      	//在setTransactionSuccessful和endTransaction之间不进行任何数据库操作
    } catch (Exception e){

    } finally {
	//当所有操作执行完成后结束一个事务
	db.endTransaction();
    }

有2点需要注意的是:

  1. 一定要调用db.setTransactionSuccessful();事务才会成功提交完成
  2. 事务是可以嵌套的

以上2点也是自己开发中犯错了才觉察到的:没有调用db.setTransactionSuccessful();发现数据没有插入;想当然的认为事务不可以嵌套。而Android的源码中也很清楚的说明了这2点,所以究其根本原因是对事务处理不够熟悉,对Android中事务的处理不熟悉。在此记录警示自己!

以下贴出Android中相关连的源代码,来自android.database.sqlite.SQLiteDatabase:

    /**
     * Begins a transaction in EXCLUSIVE mode.
     * <p>
     * Transactions can be nested.
     * When the outer transaction is ended all of
     * the work done in that transaction and all of the nested transactions will be committed or
     * rolled back. The changes will be rolled back if any transaction is ended without being
     * marked as clean (by calling setTransactionSuccessful). Otherwise they will be committed.
     * </p>
     * <p>Here is the standard idiom for transactions:
     *
     * <pre>
     *   db.beginTransaction();
     *   try {
     *     ...
     *     db.setTransactionSuccessful();
     *   } finally {
     *     db.endTransaction();
     *   }
     * </pre>
     */
    public void beginTransaction() {
        beginTransaction(null /* transactionStatusCallback */, true);
    }

注释中说明的很清楚:事务可以嵌套,事务标记为成功才会提交,否则直接回滚。