zoukankan      html  css  js  c++  java
  • SQLite之rowid与sqlite3_last_insert_rowid()

    //返回最后一次insert的rowid,如果没有插入就返回0 (DB session断开后也返回0, 是保存在进程的内存中)
    SELECT LAST_INSERT_ROWID();
    
    
    //找到最大的rowid(如果是自定义的primaryKey, 比如 NumID  则都可以用,  反正是alias 别名)
    SELECT  *,MAX(rowid) FROM Table_1004A;//推荐
    SELECT  *,MAX(NumID  ) FROM Table_1004A;//推荐
    
    
    SELECT  *,MIN(rowid) FROM Table_1004A;//推荐
    
    
    //不推荐,再增加OrderBy DESC 等等
    SELECT rowid FROM Table_1004A ORDER BY ROWID DESC LIMIT(1);
    SELECT *,rowid FROM Table_1004A ORDER BY ROWID DESC LIMIT(1);
    
    
    SELECT *,rowid "NAVICAT_ROWID" FROM "main"."Table_1004A" LIMIT 53000,1000
    
    
    //时间: 0.03s
    INSERT INTO "main"."Table_1004A"("ChipID", "ChipType", "BatchID", "T1_TestMode", "T1_Timestamp", "T1_Temp", "T1_ErrSaAddrNum", "T1_ErrSaAddr", "T1_ChipResult", "T1_HandlerResult", "T2_TestMode", "T2_Timestamp", "T2_Temp", "T2_ErrSaAddrNum", "T2_ErrSaAddr", "T2_ChipResult", "T2_RepairedSaAddr", "T2_HandlerResult", "Comment") VALUES (1301000100005001, 'XM1004_A_DWL', 100, 'ArrayWR', 1571106878, 120, 5, '1,2,3,4,5', 'Finish_MarchC', 1, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL);
    
    
    //结果显示53102 + 显示最后插入信息
    SELECT LAST_INSERT_ROWID();
    SELECT *,rowid FROM Table_1004A WHERE rowid= 53102;
    
    
    //2句话,一句搞定
    SELECT *,rowid FROM Table_1004A WHERE rowid=LAST_INSERT_ROWID();
    
    
    1、背景知识
    
    (1). ROWID
    
    每个表默认都有 rowid 列,除非创建表时指定了 WITHOUT ROWID, 它现在是 64 位长的。在查询时用 select * from table1 里没有它,要显式的用 select rowid, * from table1 就会列出它来。
    
    (2). ROWID 的别名
    
    ROWID 除了可用 rowid 查出它之外,还可用别名 _ROWID_ 和 OID,都不分大小写的, 例如 select oid from table1。另外我们还可以自定义一个 ROWID 的别名,用 INTEGER PRIMARY KEY 标识的列也是 ROWID 的一个别名,比如我们用 id 来作为 ROWID 的别名。
    
    ROWID 的表示也是个自增列,每个表有自己的计数器,和常见的数据库的自增列是一致的。
    
    SQLite 的 ROWID 可不象 Oracle 的 ROWID, Oracle 的 ROWID 是纯内部的,标记着记录的物理位置,所以数据库导入导出 Oracle 的 ROWID 就会变了。更为可怕的是 SQLite 的 ROWID 是可以自己赋值的。
    
    (3). 自增列序列表(也是 ROWID)
    
    用 INTEGER PRIMARY KEY AUTOINCREMENT 标识的列就是个自增列,说到底它也是 ROWID  别名。数据库中存在自增列后,SQLite 就会创建一个 sqlite_sequence 表。所有表的自增列都共享这个表,sqlite_sequence 分别维护着每个自增列的当前值,所以自增列的计数也是单独的。它不象于 Oracle 中多个表在共用一个序列时,ID 值是交错的,Oracle 的序列的好处就是插入前可获知下一个序列值。
    
    
    顺便说一下 VACUUM命令,这个命令能重建 ROWID 值。
    
    https://yanbin.blog/sqlite-primary-rowid-autoincrement/
    
    
    2、插入时注意事项
    
    (1)当主键设置为自动增长的时候,主键的数据类型必须是integer类型,不能使long类型。
    
    (2)插入的时候,如果罗列的列中没有自动增长列 ,自动增长列也是可以实现自动增长的,如一所示。
    
    (3)插入的时候,如果罗列的列中有自动增长列,那么设置为null,可以实现自动增长,如二所示。
    
    https://blog.csdn.net/scyatcs/article/details/12625521
    
    
    3、读取刚插入的记录的ID
    
    select last_insert_rowid() from 表名
    
    
    
    SQLite数据库中的表均有一个特殊的rowid字段,它是一个不重复的64位有符号整数,默认起始值为1。
    
    rowid别名为oid或_rowid_,但在创建表的SQL声明语句中只能使用rowid作为关键字。如果在创建表的时候设置了类型为integer的具有自动增长性的主键,那么这时的主键相当于是rowid的别名。
    
    rowid只能是单调递增的,它由SQLite内部维护,不能自己指定。对于失败的插入操作,rowid也可能在原来的基础上执行了自增。删除或回滚操作并不会减小rowid的值。当rowid达到所能表示的最大值时,这时如果有新纪录要插入,系统就会从之前没有被使用过的(或从已经被删除的记录的)rowid中随机取出一个作为rowid。若没有可用的rowid,系统就会抛出SQLITE_FULL的错误。
    
    rowid字段在表中默认是隐藏的,也就是说,除非SQL查询语句中指定返回rowid,否则查询结果不会包含有rowid字段。
    
    可以在创建表时使用WITHOUT ROWID以声明不生成rowid字段,例如:
    
    CREATE TABLE IF NOT EXISTS wordcount(
    
     word TEXT PRIMARY KEY,
    
     cnt INTEGER
    
    ) WITHOUT ROWID;
    
    将关键字AUTOINCREMENT使用在声明为WITHOUT ROWID的表不但不起作用,还将引发一个错误。
    
    SQLiteAPI 函数sqlite3_last_insert_rowid()可以取得最后一条插入的记录的rowid。但sqlite3_last_insert_rowid()是基于当前进程的。也就是说,sqlite3_last_insert_rowid()取到的是当前进程最后一次插入记录的rowid。对于不是当前进程插入的记录,sqlite3_last_insert_rowi()均返回0。sqlite3_last_insert_rowi()对应的SQL声明为last_insert_rowid(),例如:
    
    select last_insert_rowid() from exam_tbl
    

    ————————————————
    版权声明:本文为CSDN博主「venchia_lu」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
    原文链接:https://blog.csdn.net/venchia_lu/article/details/50457274

  • 相关阅读:
    Delphi XE5 android 蓝牙通讯传输
    Delphi XE5 android toast
    Delphi XE5 android openurl(转)
    Delphi XE5 如何设计并使用FireMonkeyStyle(转)
    Delphi XE5 android 捕获几个事件
    Delphi XE5 android listview
    Delphi XE5 android 黑屏的临时解决办法
    Delphi XE5 android popumenu
    Delphi XE5 android 获取网络状态
    Delphi XE5 android 获取电池电量
  • 原文地址:https://www.cnblogs.com/scotth/p/11676192.html
Copyright © 2011-2022 走看看