Android SQLite 事务处理 Operation SQLite

在写蓝牙Contacts的时候,遇到一个问题,多联系人(最少1000+)插入导致应用程序死掉,因为我们写的蓝牙不是设备的标准蓝

牙,自己焊接的,协议都是不同的,数据传递虽然都是一样的方式,但是驱动和连接协议有别于标准蓝牙,这里就不细说了,

直接切入主题,解决这个蓝牙跟车机设备联系人同步的问题

先前有几个客户反馈说,在测试我们蓝牙应用的时候,说联系人超1000+的时候,或者超了300+,都会导致程序死掉,或者上传很慢,因为先前蓝牙应用

是其他同事写的,不知道这个情况,之后一个朋友(袁工)说建议采用事物处理,我今天亲测了,确实事物跟单事物插入的效果真是天差地别啊!好明

显!!

首先说说事物,直截了当的说吧,每一个语句就是一个事物,然后频繁的操作 SQLite 会导致应用缓不过来,而我们可以把要做的操作全部归纳到一个事

物里面去,需要我们调用三个函数 

SQLiteDatabase db:

db.beginTransaction(); // 开启事务

db.setTransactionSuccessful();// 设置事物标志为成功,当结束事物时就会提交事物

db.endTransaction();//事物结束

SQLiteOpenHelper  Demo:

package com.example.uploadphonebook;

import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.util.Log;

public class PhoneBookeHelper extends SQLiteOpenHelper{
    @SuppressWarnings("unused")
	private Context mContext;
    private static PhoneBookeHelper mPhoneBookeHelper;
    public static final String DB_NAME = "phonebook";
    public static final String ID = "_id";
    public static final String NAME = "name";
    public static final String NUMBER = "number";
    private static final int VERSION = 1;
	private static final String BOOK_TABLE_NAME = "contacts";
	public static final String CREATE_TABLE = String
			.format("create table if not exists %s (%s integer primary key autoincrement, %s text, %s text)",
					BOOK_TABLE_NAME, ID,NAME, NUMBER);
    private PhoneBookeHelper(Context context) {
        super(context, DB_NAME, null, VERSION);
        this.mContext = context;
        Log.d("BlueTooth_Navi_Call", "SQLiteatabase is Create...");
    }
    public static PhoneBookeHelper getPhoneBook(Context context){
    	if(mPhoneBookeHelper==null){
    		mPhoneBookeHelper = new PhoneBookeHelper(context);
    		Log.d("BlueTooth_Navi_Call", "mPhoneBookeHelper is null...");
    	}
    	Log.d("BlueTooth_Navi_Call", "mPhoneBookeHelper is not null...");
    	return mPhoneBookeHelper;
    }

	@Override
	public void onCreate(SQLiteDatabase db) {
        db.execSQL(CREATE_TABLE);
        Log.d("BlueTooth_Navi_Call", "SQLite Database Table is Create...");
	}

	@Override
	public void onUpgrade(SQLiteDatabase arg0, int arg1, int arg2) {

	}
	public void insertContacts(){
		Log.d("BlueTooth_Navi_Call", "SQLite Database Start is insert...");
		SQLiteDatabase db = getWritableDatabase();
		db.beginTransaction();// 开启事务
		try {
			for(int i = 0;i<=10000;i++){
				String name = "Tom"+i;
				String number = "185"+Math.random()*100000000;
				String url = "insert into contacts (name,number) values(?,?)";
						db.execSQL(url, new String[]{name,number});
				Log.d("BlueTooth_Navi_Call", "******************************"+name +" "+ number+"******************************");
			}
			db.setTransactionSuccessful();// 设置事物标志为成功,当结束事物时就会提交事物
		} finally{
			db.endTransaction();
		}
		db.close();
		Log.d("BlueTooth_Navi_Call", "SQLite Database end for insert...");
	}

}

插入Demo:

package com.example.uploadphonebook;

import android.os.Bundle;
import android.os.Handler;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.app.Activity;
public class MainActivity extends Activity implements OnClickListener{
    private PhoneBookeHelper mPhoneBookeHelper;
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		Button upload = (Button)findViewById(R.id.Upload);
		upload.setOnClickListener(this);
		mPhoneBookeHelper = PhoneBookeHelper.getPhoneBook(this);
	}
	@Override
	public void onClick(View view) {
		Log.d("BlueTooth_Navi_Call", "UploadPhoneBook is Start...");
		mHandler.sendEmptyMessage(0);
//		new Thread(new Runnable() {
//			@Override
//			public void run() {
//				mPhoneBookeHelper.insertContacts();
//				Log.d("BlueTooth_Navi_Call", "UploadPhoneBook is Successful");
//				Toast.makeText(getApplicationContext(), "UploadPhoneBook is Successful", Toast.LENGTH_SHORT).show();
//			}
//		}).start();
	}
	private Handler mHandler = new Handler(){
		public void handleMessage(android.os.Message msg) {
			int code = msg.what;
			switch (code) {
			case 0:
				mPhoneBookeHelper.insertContacts();
				break;
			}
		}
	};
}

大家需要注意的是,在Activity里新建线程的时候,它是不能直接访问Activity里的UI组件的,需要用Handler或者AsynTask来处理,否者会抛出Exception:

java.lang.RuntimeException: Can‘t create handler inside thread that has not called Looper.prepare()

所以我在按钮事件里调用sendEmptyMessage()函数,执行插入操作

经测试,插入1000+, 耗时0.9s,而单事物耗时将近7s

10000+,耗时12左右,单事物2分09s

所以效果是很明显的,下面看看实测对比图:

单事物插入,1000+测试:

		for(int i = 0;i<=1000;i++){
			String name = "Tom"+i;
			String number = "185"+Math.random()*100000000;
			String url = "insert into contacts (name,number) values(?,?)";
					db.execSQL(url, new String[]{name,number});
			Log.d("BlueTooth_Navi_Call", "******************************"+name +" "+ number+"******************************");
		}

归纳事物,1000+测试:

			db.beginTransaction();// 开启事务
		try {
			for(int i = 0;i<=1000;i++){
				String name = "Tom"+i;
				String number = "185"+Math.random()*100000000;
				String url = "insert into contacts (name,number) values(?,?)";
						db.execSQL(url, new String[]{name,number});
				Log.d("BlueTooth_Navi_Call", "******************************"+name +" "+ number+"******************************");
			}
			db.setTransactionSuccessful();// 设置事物标志为成功,当结束事物时就会提交事物
		} finally{
			db.endTransaction();
		}
		db.close();
		Log.d("BlueTooth_Navi_Call", "SQLite Database end for insert...");

1000+ 耗时-对比图:

10000+ 测试代码同上,就是多了一个0而已,耗时对比图:

效果是不是很明显?误差不是很大估计也就1s左右~

时间: 2024-10-29 19:07:22

Android SQLite 事务处理 Operation SQLite的相关文章

Android学习笔记(42):SQLite数据库

(1)SQLite数据库 先简单介绍一下SQLite数据库: 2000年由D.Richard Hipp发布. 是一款轻型.开源嵌入式关系数据库,占用资源非常低.目前用于很多嵌入式产品中,在嵌入式设备中,SQLite可能只需要几百K的内存就够了. 与Mysql.PostgreSQL这两款开源世界著名的数据库管理系统相比,它的处理速度更快. 在Android平台下,除了可以在Android程序中操作SQLite数据库之外,还可以在命令行模式下进行各种数据库的操作,包括表的各种操作,对数据的增加.删除

Android数据存储之SQLite的操作

Android作为一个应用在移动设备上的操作系统,自然也就少不了数据的存储.然而SQLite作为一个轻型的关系型数据库,基于其轻量.跨平台.多语言接口及安全性等诸多因数考虑,因而Android较大的数据存储采用了SQLite.SQLite与大多数关系型数据库一样都遵循ACID,语法也非常相似.只要您懂得mysql.sqlserver等关系型数据库的操作,只要查看下SQLite的官方文档便可快速上手.SQLite语法您可通过http://sqlite.org/lang.html进行查看. 接下来看

Android开发中的SQLite优化

关于SQLite的优化,首先是能用SQL语句批次处理的,就不要单笔操作,Cursor就更是能不用就不用.比如成批的DELETE/UPDATE,将条件组装到SQL语句,会比使用CURSOR一条条的查再删效率要高很多(若干年前就曾使用存储过程代替单笔操作,将一次批量计算时间从一天缩到了数分钟以内,参考).其次是对操作的优化:对于INSERT/UPDATE操作较多时使用事务,如果SELECT操作较多时,使用索引. 结合现在的工作,发现针对操作的优化,下面这篇文章可以翻译出来归档.以下为正文: SQLi

Android 查看和管理sqlite数据库

在Android中可以使用Eclipse插件DDMS来查看,也可以使用Android工具包中的adb工具来查看.android项目中的sqlite数据库位于/data/data/项目包/databases中. 使用DDMS导出sqlite数据库. 1.首先打开android项目的调试模式,然后找到显示DDMS: 选择DDMS 2.切换到DDMS,显示File Explorer窗口,找到/data/data/ 然后找到程序包的文件夹,打开databases,就能看到sqlite数据库文件了.选择将

android数据存储之Sqlite(二)

SQLite学习笔记 前言:上一章我们介绍了sqlite的一些基本知识以及在dos命令下对sqlite进行的增删改查的操作,这一章我们将在android项目中实际来操作sqlite. 1. SQLiteDatabase的介绍 Android提供了创建和是用SQLite数据库的API.SQLiteDatabase代表一个数据库对象,提供了操作数据库的一些方法.在 Android的SDK目录下有sqlite3工具,我们可以利用它创建数据库.创建表和执行一些SQL语句.下面是SQLiteDatabas

C#程序员学习Android开发系列之SQLite

上篇博客提到过SQLite,它是嵌入式数据库,由于其轻巧但功能强大,被广泛的用于嵌入式设备当中.后来在智能手机.平板流行之后,它作为文件型数据库,几乎成为了智能设备单机数据库的必选,可以随着安卓app打包到apk文件当中. SQLite的官方网站是http://www.sqlite.org/,可以任意下载,上面也有详尽的文档可以参考,这篇博客重点关注SQLite在Android开发中如何使用. 在Android开发中,推荐建立一个类继承自SQLiteOpenHelper来创建数据库操作类,比如:

【转载】Android数据存储之SQLite

SQLite是D.Richard Hipp用C语言编写的开源嵌入式数据库引擎.它支持大多数的SQL92标准,并且可以在所有主要的操作系统上运行. 在Android中创建的SQLite数据库存储在:/data/data/<包名>/databases/目录下. 主要特点: -轻量级 -独立性,没有不依赖,无需安装 -跨平台,支持众多操作系统 -支持高达2TB大小的数据库 -每个数据库以单个文件的形式存在 -以B-Tree的数据结构形式存储在硬盘 SQLite的数据类型: SQLite支持NULL.

Android数据存储之SQLite使用

SQLite是D.Richard Hipp用C语言编写的开源嵌入式数据库引擎.它支持大多数的SQL92标准,并且可以在所有主要的操作系统上运行. 在Android中创建的SQLite数据库存储在:/data/data/<包名>/databases/目录下. 主要特点: -轻量级 -独立性,没有不依赖,无需安装 -跨平台,支持众多操作系统 -支持高达2TB大小的数据库 -每个数据库以单个文件的形式存在 -以B-Tree的数据结构形式存储在硬盘 SQLite的数据类型: SQLite支持NULL.

Android技术8:SQLite数据升级

由于应用程序的升级,往往伴随着数据库的升级,数据库升级一般设计表的增加与删除,表添加删除字段,数据的备份等操作. 1.数据库升级 我们都通过继承SQLiteOpenHelper类,实现对数据库的操作和版本升级等.版本升级有关方法 onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion); 当版本号大于当前数据库版本号,会调用onUpgrade方法. 2.演示数据库升级 对于表的增删相对比较简单,下面演示添加字段. 2.1原始数据库s

Android开发之利用SQLite进行数据存储

Android开发之利用SQLite进行数据存储 Android开发之利用SQLite进行数据存储 SQLite数据库简单介绍 Android中怎样使用SQLite 1 创建SQLiteOpenHelper对象并创建表 2 通过SQLiteDatabase对象运行增删改查操作 3 SQLiteDatabase之事务transaction 1.SQLite数据库简单介绍 SQLite.是一款轻型的数据库,是遵守ACID的关系型数据库管理系统,它包括在一个相对小的C库中.它是D.RichardHip