赞
踩
SQLite是Android内置的一个小型、关系型、属于文本型的数据库,是一种轻量级的嵌入式关系型数据库管理系统,广泛应用于移动应用开发中,包括Android平台。
用途
:在Android开发中,SQLite通常用于存储应用程序的结构化数据,例如用户信息、设置、日志等。开发者可以通过SQLite在本地设备上创建、读取、更新和删除数据库中的数据。API支持
:Android提供了SQLiteOpenHelper类和SQLiteDatabase类来管理SQLite数据库。SQLiteOpenHelper类用于创建和管理数据库的帮助类,而SQLiteDatabase类用于执行SQL语句和数据库操作。数据类型
:SQLite支持多种数据类型,包括整数、实数、文本、日期/时间等。开发者可以根据需要选择合适的数据类型来存储数据。性能
:由于SQLite是一个轻量级的数据库引擎,因此在移动设备上运行时具有较好的性能。同时,SQLite还支持事务处理和索引等功能,可以提高数据库操作的效率。
SQLiteOpenHelper类的数据库操作方法介绍:
方法名 | 作用 |
---|---|
onCreate(SQLiteDatabase db) | 当数据库第一次被创建时调用此方法。在该方法中,可以执行创建数据库表的SQL语句。 |
onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) | 当数据库需要升级时调用此方法。在该方法中,可以执行升级数据库表结构的SQL语句。 |
onDowngrade(SQLiteDatabase db, int oldVersion, int newVersion) | 当数据库需要降级时调用此方法。在该方法中,可以执行降级数据库表结构的SQL语句。 |
getWritableDatabase() | 获取一个可读/写的数据库实例,如果数据库不存在,则会调用onCreate()方法创建数据库。 |
getReadableDatabase() | 获取一个可读的数据库实例,如果数据库不存在,则会调用onCreate()方法创建数据库。 |
close() | 关闭数据库连接。 |
onOpen(SQLiteDatabase db) | 在数据库被打开时调用,可以用来执行一些初始化操作。 |
SQLiteDatabase类的数据库操作方法介绍:
方法名 | 作用 |
---|---|
execSQL (String sql) | 执行 SQL 语句,如创建表、插入数据、更新数据、删除数据等,不能进行查询操作 |
beginTransaction() | 开启事务。 |
setTransactionSuccessful() | 标记事务成功。 |
endTransaction() | 结束事务。 |
insert (String table, String nullColumnHack, ContentValues values) | 插入数据。 |
update (String table, ContentValues values, String whereClause, String[] whereArgs) | 更新数据。 |
delete (String table, String whereClause, String[] whereArgs) | 删除数据。 |
query (String table, String[] columns, String selection, String[] selectionArgs, String groupBy, String having, String orderBy) | 查询数据。 |
rawQuery(String sql, String[] selectionArgs) | 执行一条 SQL 查询语句。 |
rawQueryWithFactory(SQLiteDatabase.CursorFactory factory, String sql, String[] selectionArgs, String editTable) | 执行一条 SQL 查询语句,并使用指定的 CursorFactory 创建 Cursor。 |
beginTransactionNonExclusive() | 开启非独占事务。 |
yieldIfContendedSafely() | 尝试释放锁,如果有其他线程正在访问数据库,则等待一段时间再尝试。 |
close() | 关闭数据库连接。 |
数据库操作无外乎:“增删查改”
:
对于“增、删、改(更新)”这类对表内容变换的操作,需先调用getWritableDatabase()获得一个可写数据库对象,在执行的时候调用通用的execSQL(String sql)或或对应的操作API方法:insert()、delete()、update()
对“查”,需要调用getReadableDatabase()获得一个可读的数据库对象,然后使用query()或rawQuery()方法
查询数据库不能使用execSQL方法
涉及的方法有onCreate()、getWritableDatabase()、getReadableDatabase()
DatabaseHelper.java
public class DatabaseHelper extends SQLiteOpenHelper { /** * context:上下文对象,通常是 Activity 或 Application 的实例。 * name:数据库的名称。 * factory:用于创建 Cursor 对象的 CursorFactory,可以为 null。 * version:数据库的版本号。 */ public DatabaseHelper(@Nullable Context context, @Nullable String name, @Nullable SQLiteDatabase.CursorFactory factory, int version) { super(context, name, factory, version); } /** * context:上下文对象。 * name:数据库的名称。 * factory:CursorFactory 对象,用于创建 Cursor 实例。 * version:数据库的版本号。 * errorHandler:用于处理数据库错误的 DatabaseErrorHandler 对象,可以为 null。 */ public DatabaseHelper(@Nullable Context context, @Nullable String name, @Nullable SQLiteDatabase.CursorFactory factory, int version, @Nullable DatabaseErrorHandler errorHandler) { super(context, name, factory, version, errorHandler); } /** * context:上下文对象。 * name:数据库的名称。 * version:数据库的版本号。 * openParams:用于配置数据库打开行为的 OpenParams 对象。 */ public DatabaseHelper(@Nullable Context context, @Nullable String name, int version, @NonNull SQLiteDatabase.OpenParams openParams) { super(context, name, version, openParams); } //第一次创建数据库的时候回调该方法 //当使用getReadableDatabase()方法获取数据库实例的时候, 如果数据库不存在, 就会调用这个方法; //作用:创建数据库表:将创建数据库表的 execSQL()方法 和 初始化表数据的一些 insert()方法写在里面; @Override public void onCreate(SQLiteDatabase db) { //SQLite数据创建支持的数据类型: 整型数据,字符串类型,日期类型,二进制的数据类型 //创建了一个名为henry的表 String sql = "create table henry(id integer primary key autoincrement,name varchar(64),address varchar(64))"; //execSQL用于执行SQL语句 完成数据库的创建 db.execSQL(sql); //数据库实际上是没有被创建或者打开的,直到getWritableDatabase() 或者 getReadableDatabase() 方法中的一个被调用时才会进行创建或者打开 } @Override public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) { } }
SqliteActivity.java
public class SqliteActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_sqlite); // 创建DatabaseHelper对象 // 只执行这句话是不会创建或打开连接的 SQLiteOpenHelper dbHelper = new DatabaseHelper(SqliteActivity.this, "henry", null, 1); // 调用getReadableDatabase()或getWritableDatabase()才算真正创建或打开数据库 SQLiteDatabase sqliteDatabase = dbHelper.getReadableDatabase(); //SQLiteDatabase sqliteDatabase = dbHelper.getWritableDatabase() ; } }
生成数据库文件路径:/data/data/your_package_name/databases/your_database_name.db。
在 Android SQLite 数据库中,事务是一种用于管理一系列数据库操作的机制,可以确保这些操作要么全部成功提交,要么全部回滚。在使用事务时,通常会涉及到以下三个方法:
beginTransaction
():该方法用于开始一个事务。在调用该方法后,所有的数据库操作都将被包含在同一个事务中,直到调用 setTransactionSuccessful() 或 endTransaction()。setTransactionSuccessful
():该方法用于标记当前事务执行成功。如果在调用 setTransactionSuccessful() 之后没有调用 endTransaction(),则当前事务中的所有操作将被提交到数据库。endTransaction
():该方法用于结束事务。如果在调用 setTransactionSuccessful() 之后调用了 endTransaction(),则事务将被提交到数据库;如果没有调用 setTransactionSuccessful(),则事务将被回滚,即所有操作将被撤销。
这三个方法通常一起使用,以确保数据库操作的原子性。在一个事务中,如果所有操作都成功执行,可以调用 setTransactionSuccessful() 来标记事务成功;然后在最后调用 endTransaction() 来提交事务。如果在事务执行过程中发生了错误或异常,可以直接调用 endTransaction() 来回滚事务,使所有操作都被撤销。
步骤:创建并打开数据库(可读/写)、插入数据
涉及方法:getWritableDatabase()、insert() ,insert()也可以使用excelSQL()代替
DatabaseHelper 不变,看一下SqliteActivity
public class SqliteActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_sqlite); // 创建并打开数据库 SQLiteOpenHelper dbHelper = new DatabaseHelper(SqliteActivity.this, "henry", null, 2); SQLiteDatabase sqliteDatabase = dbHelper.getWritableDatabase(); // 创建ContentValues对象 ContentValues values = new ContentValues(); // 向该对象中插入键值对 values.put("id", 1); values.put("name", "henry handsome"); //其中,key代表列名,value代表该列要插入的值 //注:ContentValues内部实现就是HashMap,但是两者还是有差别的 //ContenValues Key只能是String类型,Value只能存储基本类型数据,不能存储对象 sqliteDatabase.beginTransaction(); // 调用insert()方法将数据插入到数据库当中 sqliteDatabase.insert("henry", null, values); // 第一个参数:要操作的表名称 // 第二个参数:空列的列名:作为第二个参数传递的是空列的列名。如果插入的数据中某些列的值为 null,可以将这些列的列名传递给该参数。 null,表示没有指定空列的列名。 // 第三个参数:ContentValues对象 sqliteDatabase.setTransactionSuccessful(); sqliteDatabase.endTransaction(); db.execSQL("insert into henry (id,name) values (1,'张三')") 也可以 sqliteDatabase.close(); } }
生成数据库文件查看:
更新数据库版本号触发onUpgrade,添加新列sex,然后在Activity中更新数据,涉及的方法有onUpgrade()、getWritableDatabase()、update()等
DatabaseHelper.java
public class DatabaseHelper extends SQLiteOpenHelper { /** * context:上下文对象,通常是 Activity 或 Application 的实例。 * name:数据库的名称。 * factory:用于创建 Cursor 对象的 CursorFactory,可以为 null。 * version:数据库的版本号。 */ public DatabaseHelper(@Nullable Context context, @Nullable String name, @Nullable SQLiteDatabase.CursorFactory factory, int version) { super(context, name, factory, version); } /** * context:上下文对象。 * name:数据库的名称。 * factory:CursorFactory 对象,用于创建 Cursor 实例。 * version:数据库的版本号。 * errorHandler:用于处理数据库错误的 DatabaseErrorHandler 对象,可以为 null。 */ public DatabaseHelper(@Nullable Context context, @Nullable String name, @Nullable SQLiteDatabase.CursorFactory factory, int version, @Nullable DatabaseErrorHandler errorHandler) { super(context, name, factory, version, errorHandler); } /** * context:上下文对象。 * name:数据库的名称。 * version:数据库的版本号。 * openParams:用于配置数据库打开行为的 OpenParams 对象。 */ public DatabaseHelper(@Nullable Context context, @Nullable String name, int version, @NonNull SQLiteDatabase.OpenParams openParams) { super(context, name, version, openParams); } //第一次创建数据库的时候回调该方法 //当使用getReadableDatabase()方法获取数据库实例的时候, 如果数据库不存在, 就会调用这个方法; //作用:创建数据库表:将创建数据库表的 execSQL()方法 和 初始化表数据的一些 insert()方法写在里面; @Override public void onCreate(SQLiteDatabase db) { //SQLite数据创建支持的数据类型: 整型数据,字符串类型,日期类型,二进制的数据类型 //创建了一个名为henry的表 String sql = "create table henry(id integer primary key autoincrement,name varchar(64),address varchar(64))"; //execSQL用于执行SQL语句 完成数据库的创建 db.execSQL(sql); //数据库实际上是没有被创建或者打开的,直到getWritableDatabase() 或者 getReadableDatabase() 方法中的一个被调用时才会进行创建或者打开 } //作用:更新数据库表结构 //调用时机:数据库版本发生变化的时候回调(取决于数据库版本) //创建SQLiteOpenHelper子类对象的时候,必须传入一个version参数 //该参数就是当前数据库版本, 只要这个版本高于之前的版本, 就会触发这个onUpgrade()方法 @Override public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) { //参数说明: // db : 数据库 //oldVersion : 旧版本数据库 //newVersion : 新版本数据库 //使用SQL的ALTER语句 String sql = "alter table henry add sex varchar(8)"; db.execSQL(sql); } }
SqliteActivity.java
public class SqliteActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_sqlite); // 传入版本号为3,大于旧版本(2),所以会调用onUpgrade()升级数据库 SQLiteOpenHelper dbHelper = new DatabaseHelper(SqliteActivity.this, "henry", null, 3); SQLiteDatabase sqliteDatabase = dbHelper.getWritableDatabase(); // 创建一个ContentValues对象 ContentValues value = new ContentValues(); value.put("sex", "man"); sqliteDatabase.beginTransaction(); // 调用update方法修改数据库 sqliteDatabase.update("henry", value, "id=?", new String[] { "1" }); // 第一个参数String:表名 // 第二个参数ContentValues:ContentValues对象(需要修改的) // 第三个参数String:WHERE表达式,where选择语句, 选择那些行进行数据的更新, 如果该参数为 null, 就会修改所有行;?号是占位符 // 第四个参数String[]:where选择语句的参数, 逐个替换 whereClause 中的占位符; sqliteDatabase.setTransactionSuccessful(); sqliteDatabase.endTransaction(); sqliteDatabase.close(); } }
看一下更新后的数据:
delete 删除的是整行而不是整列
新增一行数据并删除一下id为1的数据。
步骤:创建并打开数据库(可读/写)、删除数据
涉及到的方法:getWritableDatabase()、delete() ,delete()也可以使用excelSQL()代替
SqliteActivity.java
public class SqliteActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_sqlite); // 传入版本号为3,大于旧版本(2),所以会调用onUpgrade()升级数据库 SQLiteOpenHelper dbHelper = new DatabaseHelper(SqliteActivity.this, "henry", null, 3); ContentValues values = new ContentValues(); values.put("id", 2); values.put("name", "henry handsome2"); values.put("address", "china"); values.put("sex", "man"); SQLiteDatabase sqliteDatabase = dbHelper.getWritableDatabase(); sqliteDatabase.beginTransaction(); sqliteDatabase.insert("henry", null, values); //调用delete方法进行删除操作 sqliteDatabase.delete("henry", "id=?", new String[]{"1"}); // sqliteDatabase.execSQL("DELETE FROM henry WHERE id = 1"); // 第一个参数 "henry" 是要删除数据的表名。 // 第二个参数 "id=?" 是删除数据的条件,其中 "?" 是一个占位符,用于接收条件值。 // 第三个参数 new String[]{"1"} 是传递给条件的值,表示要删除 id 列值为 "1" 的数据。 sqliteDatabase.setTransactionSuccessful(); sqliteDatabase.endTransaction(); sqliteDatabase.close(); } }
看一下删除后的数据库:
步骤:创建并打开数据库(可读)、查询数据
涉及方法:getReadableDatabase()、query() 或 rawQuery()
query
() 方法:用于查询数据库中的数据,并返回一个 Cursor 对象,通过 Cursor 对象可以遍历查询结果。query() 方法的参数包括表名、要返回的列名、查询条件、查询条件参数等。rawQuery
() 方法:用于执行 SQL 查询语句,并返回一个 Cursor 对象。可以执行复杂的 SQL 查询语句,如联合查询等。queryWithFactory
() 方法:与 query() 方法类似,但可以指定一个 CursorFactory 对象,用于创建 Cursor 对象。rawQueryWithFactory
() 方法:与 rawQuery() 方法类似,但可以指定一个 CursorFactory 对象,用于创建 Cursor 对象。
//第一种最为简单 //将所有的SQL语句都组织到一个字符串中,使用占位符代替实际参数(selectionArgs) db.rawQuery(String sql, String[] selectionArgs); db.query(String table, String[] columns, String selection, String[] selectionArgs, String groupBy, String having, String orderBy); db.query(String table, String[] columns, String selection, String[] selectionArgs, String groupBy, String having, String orderBy, String limit); db.query(String distinct, String table, String[] columns, String selection, String[] selectionArgs, String groupBy, String having, String orderBy, String limit); //参数说明 //table:要操作的表明 //columns:查询的列所有名称集 //selection:WHERE之后的条件语句,可以使用占位符 //groupBy:指定分组的列名 //having指定分组条件,配合groupBy使用 //orderBy指定排序的列名 //limit指定分页参数 //distinct可以指定“true”或“false”表示要不要过滤重复值 //所有方法将返回一个Cursor对象,代表数据集的游标 //Cursor对象常用方法如下: c.move(int offset); //以当前位置为参考,移动到指定行 c.moveToFirst(); //移动到第一行 c.moveToLast(); //移动到最后一行 c.moveToPosition(int position); //移动到指定行 c.moveToPrevious(); //移动到前一行 c.moveToNext(); //移动到下一行 c.isFirst(); //是否指向第一条 c.isLast(); //是否指向最后一条 c.isBeforeFirst(); //是否指向第一条之前 c.isAfterLast(); //是否指向最后一条之后 c.isNull(int columnIndex); //指定列是否为空(列基数为0) c.isClosed(); //游标是否已关闭 c.getCount(); //总数据项数 c.getPosition(); //返回当前游标所指向的行数 c.getColumnIndex(String columnName);//返回某列名对应的列索引值 c.getString(int columnIndex); //返回当前行指定列的值
SqliteActivity.java
public class SqliteActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_sqlite); // 传入版本号为3,大于旧版本(2),所以会调用onUpgrade()升级数据库 SQLiteOpenHelper dbHelper = new DatabaseHelper(SqliteActivity.this, "henry", null, 3); SQLiteDatabase sqliteDatabase = dbHelper.getWritableDatabase(); sqliteDatabase.beginTransaction(); Cursor cursor = sqliteDatabase.query("henry", new String[]{"id", "name","address","sex"}, "id IN (?, ?)", new String[]{"2","3"}, null, null, null); // "henry":表示要查询的表名,即要从名为 "henry" 的表中查询数据。 // new String[]{"id",name","address","sex"}:表示要返回的列名, // "id IN (?, ?)":表示查询条件,这里是根据 id 进行查询。 // new String[]{"2","3"}:表示查询条件的值,即要查询的 id 值为 2和3。 // null, null, null:分别表示查询结果的排序方式、分组方式和筛选方式,这里都设置为 null,表示不进行排序、分组和筛选。 // 将光标移动到下一行,从而判断该结果集是否还有下一条数据 //如果有则返回true,没有则返回false // while (cursor.moveToNext()) { // id = cursor.getString(cursor.getColumnIndex("id")); // name = cursor.getString(cursor.getColumnIndex("name")); // } ArrayList list=cursor2list(cursor); sqliteDatabase.setTransactionSuccessful(); sqliteDatabase.endTransaction(); sqliteDatabase.close(); Log.d("henry------"," "+list.toString()); } //也可将Cursor中的数据转为 ArrayList<Map<String, String>> 类型数据 @SuppressLint("Range") private ArrayList<Map<String, String>> cursor2list (Cursor cursor){ ArrayList<Map<String, String>> list = new ArrayList<Map<String, String>>(); //遍历Cursor while (cursor.moveToNext()) { Map<String, String> map = new HashMap<String, String>(); map.put("id", cursor.getString(cursor.getColumnIndex("id"))); map.put("name", cursor.getString(cursor.getColumnIndex("name"))); map.put("address", cursor.getString(cursor.getColumnIndex("address"))); map.put("sex", cursor.getString(cursor.getColumnIndex("sex"))); list.add(map); } return list; } }
私自又添加了行数据:
当我们完成了对数据库的操作后,记得调用SQLiteDatabase的close()方法释放数据库连接,否则容易出现SQLiteException。
SQLiteOpenHelper dbHelper = new DatabaseHelper(SqliteActivity.this,
"henry", null, 3);
// 调用getReadableDatabase()方法创建或打开一个可以读的数据库
//通过返回的SQLiteDatabase对象对数据库进行操作
SQLiteDatabase sqliteDatabase = dbHelper.getReadableDatabase();
//关闭当前数据库
sqliteDatabase.close();
想要删除数据库时,使用如下:
SQLiteOpenHelper dbHelper = new DatabaseHelper(SqliteActivity.this,
"henry", null, 3);
SQLiteDatabase sqliteDatabase = dbHelper.getReadableDatabase();
deleteDatabase("henry");
诺,数据库文件没有了
deleteDatabase() 是 Context 类中的一个方法,用于删除应用程序的数据库。该方法的参数详解如下:
- 参数
String name
:
表示要删除的数据库的名称。通常情况下,数据库的名称对应于应用程序的包名,加上数据库文件的扩展名(例如 mydatabase.db)。
如果数据库文件存储在默认位置(即应用程序的私有目录中),则只需传入数据库文件的名称即可。
如果数据库文件存储在其他位置,需要传入完整的数据库文件路径。- 返回类型
boolean
:
表示删除操作是否成功。
如果成功删除数据库文件,则返回 true;否则返回 false。
示例用法:
String databaseName = "mydatabase.db";
boolean isDeleted = context.deleteDatabase(databaseName);
if (isDeleted) {
Log.d(TAG, "数据库删除成功");
} else {
Log.d(TAG, "数据库删除失败");
}
特别注意
其实对于上述所有的数据库操作(除了“查询”),我们都可以使用下列方法代替:
db.executeSQL(String sql);
db.executeSQL(String sql, Object[] bindArgs);
//sql语句中使用占位符,然后第二个参数是实际的参数集
建议都使用SQL语句,因为:
SQL语句较为通用;
使用insert()、delete()、query()方法具备多个参数,使用复杂。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。