Android数据库开发——SQLite

简介: 上篇博客提到过SQLite,它是嵌入式数据库,由于其轻巧但功能强大,被广泛的用于嵌入式设备当中。

上篇博客提到过SQLite,它是嵌入式数据库,由于其轻巧但功能强大,被广泛的用于嵌入式设备当中。后来在智能手机、平板流行之后,它作为文件型数据库,几乎成为了智能设备单机数据库的必选,可以随着安卓app打包到apk文件当中。

SQLite的官方网站是http://www.sqlite.org/,可以任意下载,上面也有详尽的文档可以参考,这篇博客重点关注SQLite在Android开发中如何使用。

在Android开发中,推荐建立一个类继承自SQLiteOpenHelper来创建数据库操作类,比如:

public class DBHelper extends SQLiteOpenHelper {

	private static final String database = "test.db";
	private static final Integer version = 1;

	public DBHelper(Context context) {

		// 构造函数初始化各成员变量
		super(context, database, null, version);
	}

	@Override
	public void onCreate(SQLiteDatabase db) {

		// 当通过SQLiteOpenHelper的子类获取数据库连接时,如果数据库不存在,则调用onCreate方法来创建数据库
		String sql = "create table Score(id integer primary key autoincrement,name varchar(20),point integer)";
		db.execSQL(sql);
	}

	@Override
	public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
		// 当传入的实例的数据库版本号高于之前的版本号时,系统会自动调用onUpgrade方法更新数据库
		// 更新数据库的操作:备份数据库表数据,重新创建或修改表、约束等,然后将原来的数据导入到新建的表中。

	}
}
上面的代码有3点需要注意:

1、构造函数(方法)中指定了数据库的名称和版本号

它会默认的在data/data/包名/databases/目录下创建这个数据库,当然你也可以指定数据库文件存在的路径;版本号设置为1,如果你要想升级,可以在构造方法的参数中加上version,以便初始化。


2、onCreate是在数据库文件没有创建的时候执行,如果有了的话则不执行

3、onUpgrade是在新的指定版本号高于旧的指定版本号的时候执行,一般在数据库升级的时候需要操作

然后我们建一个具体的数据库操作类:

/**
 * 成绩操作类
 * 
 * @author guwei
 * 
 */
public class ScoreOp {

	// 插入一条成绩记录
	public long insert(SQLiteDatabase db, String name, Integer point) {
		try {
			db.beginTransaction();
			ContentValues values = new ContentValues();
			values.put("name", name);
			values.put("point", point);
			long result = db.insert("Score", null, values);
			if (result != -1) {
				db.setTransactionSuccessful();
			}
			return result;
		} finally {
			db.endTransaction();
		}
	}

	// 修改一条成绩记录
	public int update(SQLiteDatabase db, String name, Integer point) {
		try {
			db.beginTransaction();
			ContentValues values = new ContentValues();
			values.put("name", name);
			values.put("point", point);
			int result = db.update("Score", values, "name = ?",
					new String[] { name });
			db.setTransactionSuccessful();
			return result;
		} finally {
			db.endTransaction();
		}
	}

	// 删除一条成绩记录
	public long delete(SQLiteDatabase db, String name) {
		try {
			db.beginTransaction();
			int result = db.delete("Score", "name = ?", new String[] { name });
			db.setTransactionSuccessful();
			return result;
		} finally {
			db.endTransaction();
		}
	}

	// 查询根据name正向排序的前10条总分大于指定分数的人员信息
	public Cursor query(SQLiteDatabase db, Integer point) {
		return db.query("Score",
				new String[] { "name", "sum(point) as points" }, null, null,
				"name", "sum(point)>=" + point, "name asc", "0,10");
	}

	// 更灵活的查询,SQL任意拼接
	public Cursor query(SQLiteDatabase db, String sql, String[] selectionArgs) {
		return db.rawQuery(sql, selectionArgs);
	}
}
这上面封装了CRUD操作,而且都是带事务的(执行多条SQL时需要),值得关注的是最后的两个query方法。

第一个query是指定了一个复杂sql查询语句的情况。

按照顺序,参数的含义如下:

1)、table The table name to compile the query against.   

指定的查询的表名

2)、columns A list of which columns to return. Passing null will return all columns, which is discouraged to prevent reading data from storage that isn't going to be used.

返回的查询列表的列名

3)、selection A filter declaring which rows to return, formatted as an SQL WHERE clause (excluding the WHERE itself). Passing null will return all rows for the given table.

where条件,不包括where关键字

4)、selectionArgs You may include ?s in selection, which will be replaced by the values from selectionArgs, in order that they appear in the selection. The values will be bound as Strings.

where条件指定的参数值

5)、groupBy A filter declaring how to group rows, formatted as an SQL GROUP BY clause (excluding the GROUP BY itself). Passing null will cause the rows to not be grouped.

group by分组后面跟着的列名

6)、having A filter declare which row groups to include in the cursor, if row grouping is being used, formatted as an SQL HAVING clause (excluding the HAVING itself). Passing null will cause all row groups to be included, and is required when row grouping is not being used.
having 后面紧跟着的在分组基础上进一步筛选的内容

7)、orderBy How to order the rows, formatted as an SQL ORDER BY clause (excluding the ORDER BY itself). Passing null will use the default sort order, which may be unordered.

order by后面根据某字段排序

8)、limit Limits the number of rows returned by the query, formatted as LIMIT clause. Passing null denotes no LIMIT clause.
limit关键字,分页查询时使用

实际上上面对应的这8个参数,就是对应如下SQL查询语句各关键字后面的内容,其原理就是通过指定参数拼接如下SQL语句。

这里顺便提一下,SQLite Expert是非常好用的管理SQLite数据库的工具,可以在http://www.sqliteexpert.com/下载到,也可以直接搜索下载相应破解版本。

回到第二个query方法,参数很简单,只有一个sql语句以及一个string数组(提供sql语句参数的值)。这个方法的意义就在于它很灵活,可以直接把能够执行的sql扔进去执行,而且是参数化的,是第一种查询方法很有力的补充。

好,最后我们就可以写测试代码来验证了。界面很简单,直接放置一个按钮即可。

public class SQLiteActivity extends Activity {  
  
    @Override  
    protected void onCreate(Bundle savedInstanceState) {  
        super.onCreate(savedInstanceState);  
        setContentView(R.layout.activity_sqlite);  
  
        Button btn = (Button) findViewById(R.id.btn);  
        btn.setOnClickListener(new View.OnClickListener() {  
  
            @Override  
            public void onClick(View v) {  
                DBHelper dbHelper = new DBHelper(SQLiteActivity.this);  
                  
                //获得一个可写数据库操作对象  
                SQLiteDatabase wdb = dbHelper.getWritableDatabase();  
                  
                //添加纪录  
                ScoreOp scoreOp = new ScoreOp();  
                scoreOp.insert(wdb, "zhang3", 98);  
                scoreOp.insert(wdb, "zhang3", 94);  
  
                scoreOp.insert(wdb, "li4", 92);  
                scoreOp.insert(wdb, "wang5", 89);  
                scoreOp.insert(wdb, "wang5", 82);  
  
                //修改记录  
                scoreOp.update(wdb, "li4", 90);  
  
                //删除记录  
                scoreOp.delete(wdb, "li4");  
  
                //获得一个可读数据库操作对象  
                SQLiteDatabase rdb = dbHelper.getReadableDatabase();  
                  
                // 1.可以调用系统提供的query方法,以指定参数的形式返回Cursor对象  
                // Cursor cursor = scoreOp.query(rdb, 192);  
  
                // 2.可以直接执行SQL查询语句  
                Cursor cursor = scoreOp  
                        .query(rdb,  
                                "select name,sum(point) as points from Score group by name having sum(point)>=192 order by name asc limit ?,?",  
                                new String[] { "0", "10" });  
                while (cursor.moveToNext()) {  
                    String name = cursor.getString(cursor  
                            .getColumnIndex("name"));  
                    Integer points = cursor.getInt(cursor  
                            .getColumnIndex("points"));  
  
                    Toast.makeText(SQLiteActivity.this,  
                            "姓名:" + name + ";总分:" + points, Toast.LENGTH_SHORT)  
                            .show();  
                }  
                cursor.close();  
            }  
        });  
  
    }  
  
}  


点击按钮执行之后就可以弹出符合条件的数据。如果不放心,可以切换到DDMS界面,选择File Explorer选项卡,找到路径下的我们创建的test.db文件,Pull(拉取)到电脑磁盘上,用SQLite Expert等工具打开验证。




目录
相关文章
|
8天前
|
搜索推荐 前端开发 API
探索安卓开发中的自定义视图:打造个性化用户界面
在安卓应用开发的广阔天地中,自定义视图是一块神奇的画布,让开发者能够突破标准控件的限制,绘制出独一无二的用户界面。本文将带你走进自定义视图的世界,从基础概念到实战技巧,逐步揭示如何在安卓平台上创建和运用自定义视图来提升用户体验。无论你是初学者还是有一定经验的开发者,这篇文章都将为你打开新的视野,让你的应用在众多同质化产品中脱颖而出。
35 19
|
4天前
|
关系型数据库 MySQL 数据库
Python处理数据库:MySQL与SQLite详解 | python小知识
本文详细介绍了如何使用Python操作MySQL和SQLite数据库,包括安装必要的库、连接数据库、执行增删改查等基本操作,适合初学者快速上手。
51 15
|
8天前
|
JSON Java API
探索安卓开发:打造你的首个天气应用
在这篇技术指南中,我们将一起潜入安卓开发的海洋,学习如何从零开始构建一个简单的天气应用。通过这个实践项目,你将掌握安卓开发的核心概念、界面设计、网络编程以及数据解析等技能。无论你是初学者还是有一定基础的开发者,这篇文章都将为你提供一个清晰的路线图和实用的代码示例,帮助你在安卓开发的道路上迈出坚实的一步。让我们一起开始这段旅程,打造属于你自己的第一个安卓应用吧!
32 14
|
11天前
|
Java Linux 数据库
探索安卓开发:打造你的第一款应用
在数字时代的浪潮中,每个人都有机会成为创意的实现者。本文将带你走进安卓开发的奇妙世界,通过浅显易懂的语言和实际代码示例,引导你从零开始构建自己的第一款安卓应用。无论你是编程新手还是希望拓展技术的开发者,这篇文章都将为你打开一扇门,让你的创意和技术一起飞扬。
|
9天前
|
XML 存储 Java
探索安卓开发之旅:从新手到专家
在数字时代,掌握安卓应用开发技能是进入IT行业的关键。本文将引导读者从零基础开始,逐步深入安卓开发的世界,通过实际案例和代码示例,展示如何构建自己的第一个安卓应用。我们将探讨基本概念、开发工具设置、用户界面设计、数据处理以及发布应用的全过程。无论你是编程新手还是有一定基础的开发者,这篇文章都将为你提供宝贵的知识和技能,帮助你在安卓开发的道路上迈出坚实的步伐。
20 5
|
7天前
|
开发框架 Android开发 iOS开发
安卓与iOS开发中的跨平台策略:一次编码,多平台部署
在移动应用开发的广阔天地中,安卓和iOS两大阵营各占一方。随着技术的发展,跨平台开发框架应运而生,它们承诺着“一次编码,到处运行”的便捷。本文将深入探讨跨平台开发的现状、挑战以及未来趋势,同时通过代码示例揭示跨平台工具的实际运用。
|
9天前
|
XML 搜索推荐 前端开发
安卓开发中的自定义视图:打造个性化UI组件
在安卓应用开发中,自定义视图是一种强大的工具,它允许开发者创造独一无二的用户界面元素,从而提升应用的外观和用户体验。本文将通过一个简单的自定义视图示例,引导你了解如何在安卓项目中实现自定义组件,并探讨其背后的技术原理。我们将从基础的View类讲起,逐步深入到绘图、事件处理以及性能优化等方面。无论你是初学者还是有经验的开发者,这篇文章都将为你提供有价值的见解和技巧。
|
8天前
|
搜索推荐 前端开发 测试技术
打造个性化安卓应用:从设计到开发的全面指南
在这个数字时代,拥有一个定制的移动应用不仅是一种趋势,更是个人或企业品牌的重要延伸。本文将引导你通过一系列简单易懂的步骤,从构思你的应用理念开始,直至实现一个功能齐全的安卓应用。无论你是编程新手还是希望拓展技能的开发者,这篇文章都将为你提供必要的工具和知识,帮助你将创意转化为现实。
|
12天前
|
Java 调度 Android开发
安卓与iOS开发中的线程管理差异解析
在移动应用开发的广阔天地中,安卓和iOS两大平台各自拥有独特的魅力。如同东西方文化的差异,它们在处理多线程任务时也展现出不同的哲学。本文将带你穿梭于这两个平台之间,比较它们在线程管理上的核心理念、实现方式及性能考量,助你成为跨平台的编程高手。
|
8天前
|
Java Android开发 开发者
探索安卓开发:构建你的第一个“Hello World”应用
在安卓开发的浩瀚海洋中,每个新手都渴望扬帆起航。本文将作为你的指南针,引领你通过创建一个简单的“Hello World”应用,迈出安卓开发的第一步。我们将一起搭建开发环境、了解基本概念,并编写第一行代码。就像印度圣雄甘地所说:“你必须成为你希望在世界上看到的改变。”让我们一起开始这段旅程,成为我们想要见到的开发者吧!
17 0