Android开发学习教程(31)- Android SQLite使用教程

0 971

—— 不为跑赢世界,只为超越自己。

Android提供了四种不同的方式用于本地存储数据,上一篇我们讲了文件存储和SharedPreferences存储,现在我们来看 SQLite 存储。SQLite 是一个结构查询基础数据库,我们可以说它是一个关系数据库。Android 系统有内部已经实现了CRUD(创建、读取、更新、删除)操作,在 Android 的 android.database 和 android.database.sqlite 包中提供了一组可用的类。

使用 SQLite 时,可能有两种不同的方式来执行不同的操作如创建、读取、更新和删除。一种是编写原始SQL语句,另一种是使用参数化函数,或者我们可以说是参数化查询。

创建数据库

使用 SQLiteOpenHelper 类在 Android 中创建数据库非常简单。SQLiteOpenHelper 是一个抽象类,具有两个抽象方法 onCreate(SQLiteDatabase db) 和 onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) 以及更多对数据库有用的函数。每当我们需要创建数据库时,我们必须扩展 SQLiteOpenHelper 类,如下所示:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
public class SqliteManager extends SQLiteOpenHelper {
    public static final String DATABASE_NAME = "test.db";
    public static final int version = 1;
     
    public SqliteManager(Context context) {
       super(context, DATABASE_NAME, null, version);
    }
    @Override
    public void onCreate(SQLiteDatabase sqLiteDatabase) {
       String dbQuery = "CREATE TABLE test (id INTEGER PRIMARY KEY AUTOINCREMENT,name TEXT, description TEXT)";
       sqLiteDatabase.execSQL(dbQuery);
    }
    @Override
    public void onUpgrade(SQLiteDatabase sqLiteDatabase, int oldVersion, int newVersion) {
        
    }
    
}

onCreate(SQLiteDatabase sqLiteDatabase)方法在整个应用程序生命周期中只调用一次,每当第一次调用 SQLiteOpenHelper 类中的 getReadableDatabase() 或 getWritableDatabase() 函数时都会调用它,因此 SQLiteOpenHelper 类在创建后调用 onCreate() 方法数据库并实例化 SQLiteDatabase 对象。数据库名称在构造函数调用中传递。

onUpgrade(SQLiteDatabase db,int oldVersion, int newVersion)仅在升级APP版本并且数据库有更新时调用,因此需要更新版本时我们必须增加version的值,比如app从1.0.0升级到1.0.1的时候数据库需要升级的话,对应的version就要改成大于1的任何整数即可。在 onUpgrade 方法中,我们可以编写SQL语句来执行所需的任何操作。如增加一张新表,增加一条数据记录等等。

在 Sqlite 中插入、读取、删除和更新操作

执行插入、读取、删除、更新操作有两种不同的方式:

1. 编写参数化查询(推荐)

2. 编写原始SQL语句

参数化查询:这些查询使用SDK内置的函数来插入、读取、删除或更新数据。这些操作相关的函数在 SQLiteDatabase 类中提供。

原始SQL语句:这些是类似于 MySql、Sql Server 等其他数据库的 sql 查询语句,将这些SQL语句当做参数传给 rawQuery(String sql,String [] selectionArgs) 或 execSQL(String sql,Object [] bindArgs) 方法来执行操作。

注: Android 官方不建议使用原始SQL语句来执行插入、读取、更新、删除操作,建议始终使用 SQLiteDatabase 类的内置函数执行插入、查询、更新、删除操作。原因如下:

当使用原始SQL语句执行插入操作的时:

1
2
3
4
5
6
7
public void insertItem(Item item) {
    String query = "INSERT INTO " + ItemTable.NAME + " VALUES (0,?,?)";
    SQLiteDatabase db = getWritableDatabase();
    db.execSQL(query, new String[]{item.name, item.description});
    db.close();
}

在使用原始查询时,我们永远不会知道操作的结果,即db.execSQL的返回值是void类型。而使用参数化查询函数则会返回一个值来表示操作成功或失败。所以建议使用参数化查询。

插入操作

使用参数化查询执行插入操作,我们必须调用 SQLiteDatabase 类中内置的插入函数:

1
2
public long insert(String tableName,String nullColumnHack,ContentValues values)

insert()函数具有三个参数,tableName 是要插入数据表的名称。nullColumnHack可能为空,SQL不允许在插入一个完全空的行时不指定至少一个列名。如果提供的值为空,则不知道列名,并且无法插入空行。如果未设置为null,则nullColumnHack参数提供可为null的列名的名称,以便在值为空的情况下显式插入null。values是包含一行数据的键值对。键应该是列名值是列值。如果插入成功,insert 函数将返回一个 long 值,即插入的行数,否则返回 - 1。

举个栗子:

1
2
3
4
5
6
7
8
9
public void addItem(Item item) {
    SQLiteDatabase db = getWritableDatabase();
    ContentValues contentValues = new ContentValues();
    contentValues.put("name", item.name);
    contentValues.put("description", item.description);
    db.insert("Items"null, contentValues);
    db.close();
}

更新操作

更新操作与插入操作非常相似,但它需要两个额外的参数,它不需要 nullColumnHack。它共有四个参数,其中两个类似于插入函数,即 tableName 和 contentValues。另外两个是 whereClause(String) 和 whereArgs(String[]):

1
2
public int update(String tableName,ContentValues contentValues,String whereClause,String[] whereArgs)

这里 whereClause 是告诉数据库在哪里更新表中的数据,建议在 whereClause 字符串中使用占位符 ? 表示将要传递的值。类似地,whereArgs 数组将包含那些传递给对应的占位符 ? 的值。如果成功,更新函数将返回受影响的行数,否则返回 0。

举个栗子:

1
2
3
4
5
6
7
8
9
10
11
public void updateItem(Item item) {
    SQLiteDatabase db = getWritableDatabase();
    ContentValues contentValues = new ContentValues();
    contentValues.put("id", item.id);
    contentValues.put("name", item.name);
    contentValues.put("description", item.description);
    String whereClause = "id=?";
    String whereArgs[] = {item.id.toString()};
    db.update("Items", contentValues, whereClause, whereArgs);
}

删除操作

与插入和更新类似,SQLiteDatabase 类中提供了删除功能,因此删除与更新功能非常相似,除了 ContentValues 对象,因为它在删除中不需要。delete 函数有三个参数,它们与更新函数的参数完全相似,使用方式与更新函数相同。

举个栗子:

1
2
3
4
5
6
7
public void deleteItem(Item item) {
    SQLiteDatabase db = getWritableDatabase();
    String whereClause = "id=?";
    String whereArgs[] = {item.id.toString()};
    db.delete("Items", whereClause, whereArgs);
}

这里 whereClause 是可选的,传递 null 将删除表中的所有行。如果 whereClause 传递,删除函数将返回受影响的行数,否则将返回 0。

注:如果要删除所有行并要求返回删除行的计数,则将 1 作为 whereClause 传递。

查询操作

从数据库表中读取与插入、更新和删除等其他函数有点不同。SQLiteDatabase 类提供query()方法来从表中读取数据。query() 方法被不同的参数集重载。它返回Cursor对象,因此 Cursor 是一个带有查询数据的结果集,它提供了不同的功能,在读取数据时非常有用。

以下是一些重载的查询函数:

public Cursor query (String table, String[] columns, String selection, String[] selectionArgs, String groupBy, String having, String orderBy, String limit)

public Cursor query (String table, String[] columns, String selection, String[] selectionArgs, String groupBy, String having, String orderBy)

public Cursor query (boolean distinct, String table, String[] columns, String selection, String[] selectionArgs, String groupBy, String having, String orderBy, String limit)

查询重载函数中的大多数参数都是可选的,除了 table 和不同的任何其他参数都可以作为 null 传递。如果 distinct 作为 true 传递,则游标数据集将没有任何重复行。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
  public ArrayList<item> readAllItems() {
      ArrayList<item> items = new ArrayList<>();
      SQLiteDatabase db = getReadableDatabase();
      //see above point 2 function
      Cursor cursor = db.query("Items"
      null// columns - null will give all
      null// selection
      null// selection arguments
      null// groupBy
      null// having
      null// no need or order by for now;
      if (cursor != null) {
        while (cursor.moveToNext()) {
        // move the cursor to next row if there is any to read it's data
                 Item item = readItem(cursor);
                 items.add(item);
           }
        }
      return items;
  }
  private Item readItem(Cursor cursor) {
      Item item = new Item();
      item.id = cursor.getInt(cursor.getColumnIndex(ItemTable.COL_ID));
      item.name = cursor.getString(cursor.getColumnIndex(ItemTable.COL_NAME));
      item.description = cursor.getString(cursor.getColumnIndex(ItemTable.COL_DESCRIPTION));
      return item;
  }
</item></item>
收藏 (0) 打赏

感谢您的支持,我会继续努力的!

打开微信/支付宝扫一扫,即可进行扫码打赏哦,分享从这里开始,精彩与您同在
点赞 (0)

声明:本站所有文章资源,如无特殊说明或标注,均为本站网友和创作者贡献分享。如若本站内容侵犯了原著者的合法权益,可联系网站客服QQ2743319061删除。

云炬星球 安卓教程 Android开发学习教程(31)- Android SQLite使用教程 https://src.yunjunet.cn/876835.html

常见问题
  • 放心亲,我们不会为了几十块钱的东西坏了名声!
查看详情
  • 方法一:点击“立即下载.”按钮,付款后在下载弹窗的虚线框的隐藏信息里获取 方法二:在正文底部使用VIP查看隐藏的解压密码 方法三:联系【云炬网络】公众号客服获取
查看详情
  • 付款后会出现“立即下载”按钮(点击即可下载),如果下载失败也可以联系客服发订单截图补发。
查看详情
  • 登录购买会多端同步购买记录,永久可以查看反复下载;非登录购买仅将购买记录保存到本地浏览器中,浏览器cookie清除后无法再次下载。先右上角点登录,然后点击微信图标可以快速授权注册登录^_^
查看详情
  • 可以试看。点击”查看演示“或“试看预览”按钮可以试读从资料目录中节选的部分内容,也可以自己指定想试看的内容。
查看详情
  • 原因一:本站所有资源已开启有效性检测(服务器24h全自动监测),当监测到下载链接无法访问时会提示“该资源已失效,请勿购买”,遇到这种情况可以联系客服修复失效的下载链接,或直接联系客服在淘宝下单购买即可。(检测原理:购买前服务器程序会预访问下载链接,响应值为200说明资源有效允许购买,响应值为404或502等报错说明资源失效禁止购买)。原因二:上传者未启用“下载”选项。
查看详情
官方客服团队

为您解决烦忧 - 24小时在线 专业服务