sqlite数据库中自增key的设定,autoincrement 和 rowid

在用sqlite设计表时,每个表都有一个自己的整形id值作为主键,其实可以不指定这么一个id值,sqlite内部本来就会为每个表加上一个 rowid,这个rowid可以当成一个隐含的字段使用,但是由sqlite引擎来维护的,在3.0以前rowid是32位的整数,3.0以后是 64位的整数,为什么不直接使用这个内部的rowid作为每个表的id主键呢。

以下是我的界面设计图:

以下DDL代码:

大家也可以去官网看:http://www.sqlite.org/autoinc.html

用指定INTEGER PRIMARY KEY AUTOINCREMENT 和不指定自增长字段用rowid有什么区别:

使用自增长字段为主键有不少问题,比如维护或是在大型分布应用中主键冲突的解决等。在一些大型分布应用中主键一般选用guid,这可以有效的避免主键冲突,减少对主键维护的工程。当然,对于中小型的应用,自增长字段的好处更多一些,简单、快速。

Sqlite中,一个自增长字段定义为INTEGER PRIMARY KEY AUTOINCREMENT,那么在插入一个新数据时,只需要将这个字段的值指定为NULL,即可由引擎自动设定其值,引擎会设定为最大的rowid+1。当然,也可以设置为非NULL的数字来自己指定这个值,但这样就必须自己小心,不要引起冲突。当这个rowid的值大于所能表达的最大值 9223372036854775807 (3.0及以后版本的rowid最大值)后,rowid的新值会这个最大数之前随机找一个没被使用了的值。所以在rowid达到最大值前,rowid的值是严格单调增加的。 INTEGER PRIMARY KEY AUTOINCREMENT 自增长字段的算法与rowid稍微有些不同。 第一,在达到最大值后,rowid会找已被删除的字段对应的rowid作为新值,而自增长字段则会丢出一个SQLITE_FULL的错误。 第二,自增长字段在增加新值时,是找一个从没被使用过的rowid作为新值,而rowid则是找最大已存在的rowid+1。这里对应用的影响会比较大,尤其是一些对id值有依赖的元记录,只适合使用自增长字段而不能用rowid

第三,使用自增长字段,引擎会自动产生一个sqlite_sequence表,用于记录每个表的自增长字段的已使用的最大值,用户可以看到,并可以用使用 Update、Delete和Insert操作,但不建议这么使用,这会让引擎混乱。如果使用rowid,也会有这么一个内部表,用户可以维护rowid 值,但看不到。 这么看来,如果直接使用rowid来代替自增加字段,根据两者的细微的差别,需要注意是否与自己的应用冲突,如果没有冲突,那么用rowid会更快一点。


SQLite中创建自增字段,一个声明为 INTEGER PRIMARY KEY 的字段将自动增加。

从 SQLite 的 2.3.4 版本开始,如果你将一个表中的一个字段声明为 INTEGER PRIMARY KEY,那么无论你何时向该表的该字段插入一个 NULL 值,这个 NULL 值将自动被更换为比表中该字段所有行的最大值大 1 的整数;如果表为空,那么将被更换为 1。

一个新的API函数 sqlite3_last_insert_rowid() 返回最近的插入操作的整形键.

注意这个整型键始终比之前插入表中的最后一个键大1。

新键相对于表中的已有键来说是唯一的,但它可能与之前从表中删除的键值重叠。

要始终得到在整个表中唯一的键,在INTEGER PRIMARY KEY的声明之前加关键词AUTOINCREMENT.这样被选的键将总是比表中已存在的最大键大1。若可能的最大键已存在于表中,INSERT操作将失败并返回一个SQLITE_FULL错误码
SQLite 是一种轻量级的关系型数据库,常用于在移动应用程序存储和管理结构化数据。在 Android 开发SQLite 是默认提供的一种数据库。 以下是在 Android 使用 SQLite 数据库的一般步骤: 1. 定义数据库模式:定义您的数据库表结构和表之间的关系。您可以使用 SQLiteOpenHelper 类来管理数据库模式。 2. 创建数据库:使用 SQLiteOpenHelper 类的 onCreate() 方法创建数据库。 3. 升级数据库:使用 SQLiteOpenHelper 类的 onUpgrade() 方法升级数据库。 4. 执行数据库操作:使用 SQLiteDatabase 类的方法执行 SQL 查询和更新。 以下是一个简单的示例,演示如何创建 SQLite 数据库和表,以及如何插入和查询数据: 1. 定义数据库模式 ```java public class MyDatabaseHelper extends SQLiteOpenHelper { private static final String DB_NAME = "mydatabase.db"; private static final int DB_VERSION = 1; public MyDatabaseHelper(Context context) { super(context, DB_NAME, null, DB_VERSION); } @Override public void onCreate(SQLiteDatabase db) { // Create tables db.execSQL("CREATE TABLE contacts (_id INTEGER PRIMARY KEY AUTOINCREMENT, name TEXT, phone TEXT);"); } @Override public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) { // Upgrade logic } } ``` 2. 创建数据库 ```java MyDatabaseHelper helper = new MyDatabaseHelper(context); SQLiteDatabase db = helper.getWritableDatabase(); ``` 3. 插入数据 ```java ContentValues values = new ContentValues(); values.put("name", "John"); values.put("phone", "1234567890"); long rowId = db.insert("contacts", null, values); ``` 4. 查询数据 ```java Cursor cursor = db.query("contacts", null, null, null, null, null, null); while (cursor.moveToNext()) { String name = cursor.getString(cursor.getColumnIndex("name")); String phone = cursor.getString(cursor.getColumnIndex("phone")); Log.d(TAG, "Name: " + name + ", Phone: " + phone); } cursor.close(); ``` 以上是一个简单的示例,演示了如何创建和使用 SQLite 数据库。在实际开发,您可能需要根据具体的需求进行更复杂的操作,例如使用 JOIN 查询多个表之间的数据关系等。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值