此文档的原文地址为为:https://www.sqlite.org/c3ref/column_blob.html。
通常,我们都会判断sqlite3_step(pStmt)的返回值是否等于sqlITE_ROW来判断是否继续执行sqlite3_step(pStmt)。在这个过程中,每执行完一次sqlite3_step()之后,会得到Table当前行的值,这时就可以被多次调用去查询这个行的各列的值。sqlite提供多个函数来实现此过程,但均以sqlite3_column为前缀,各函数如下
const void *sqlite3_column_blob(sqlite3_stmt*,int iCol); int sqlite3_column_bytes(sqlite3_stmt*,int iCol); int sqlite3_column_bytes16(sqlite3_stmt*,int iCol); double sqlite3_column_double(sqlite3_stmt*,int iCol); int sqlite3_column_int(sqlite3_stmt*,int iCol); sqlite3_int64 sqlite3_column_int64(sqlite3_stmt*,int iCol); const unsigned char *sqlite3_column_text(sqlite3_stmt*,int iCol); const void *sqlite3_column_text16(sqlite3_stmt*,int iCol); int sqlite3_column_type(sqlite3_stmt*,int iCol); sqlite3_value *sqlite3_column_value(sqlite3_stmt*,int iCol);
其中,各函数的第一个参数为从sqlite3_prepare()返回来的prepared statement对象的指针(pStmt),第二参数为指定这一行中的想要被查询的列的索引号,在返回行中各列的索引号从左至右依次排列,最左边的的一列索引号为0,行的列数可以使用sqlite3_colum_count()来获得。
如果当前sql语句没有指向一个有效的行,或者超出了当前行列的索引值,函数返回未定义的结果。同时,这些函数只有当最后一次调用的sqlite3_step()返回了Table的当前行时才能被调用,并且sqlite3_reset()与sqlite3_finalize()函数没有被调用过,如果出现此类情况,那么函数也将返回未定义的结果。
函数sqlite3_column_bytes()返回结果列初始数据的数据类型码,数据类型码分为sqlITE_INTEGER,sqlITE_FLOAT,sqlITE_BLOB,sqlITE_NULL,sqlITE_TEXT。sqlite3_column_bytes()返回值只有在调用过程中没有发生数据类型转换时才有意义,如果在调用过程中发生数据类型转换,那么sqlite3_column_bytes()返回值为未定义。
如果sqlite3_step()的返回结果类型为BLOB或者为UTF-8字符串(即所查询的当前column的数据类型),那么sqlite3_column_bytes() 将返回该BLOB或者字符串的字节数(注意:一般UTF-8编码汉字占3个字节)。如果返回结果类型为UTF-16字符串,那么sqlite3_column_bytes()会先将UTF-16字符串先转换为UTF-8,之后再返回字符串的字节数。如果返回结果类型为一个数字值,那么sqlite3_column_bytes()使用sqlite3_snprintf将该值转换为UTF-8,之后再返回字符串的字节数。如果返回结果为NULL,sqlite3_column_bytes() 返回0。
如果sqlite3_step()的返回结果类型为BLOB或者为UTF-16字符串(即所查询的当前column的数据类型),那么sqlite3_column_bytes16() 将返回该BLOB或者字符串的字节数(注意:一般UTF-16编码汉字占4个字节)。如果返回结果类型为UTF-8字符串,那么sqlite3_column_bytes16()会先将UTF-8字符串先转换为UTF-16,之后再返回字符串的字节数。如果返回结果类型为一个数字值,那么sqlite3_column_bytes16()使用sqlite3_snprintf将该值转换为UTF-16,之后再返回字符串的字节数。如果返回结果为NULL,sqlite3_column_bytes16() 返回0。
sqlite3_column_bytes8()与sqlite3_column_bytes16()返回的字节数不包括字符串结尾包含的'\0'终止符。函数sqlite3_column_text()与sqlite3_column_text16()返回当前column内的字符串,即使是一个空字符串。
函数sqlite3_column_blob()对于一个长度0的BLOB将返回一个空指针。
//(如果当前行所要查询的column内数据类型为int,那么使用函数sqlite3_column_int()与sqlite3_column_int64()来查询该int值。如果当前行所要查询的column内数据类型为double,那么使用函数sqlite3_column_double(sqlite3_stmt*,int iCol)来查询该double值。
警告:sqlite3_column_value返回的对象是一个unprotected sqlite3_value对象。在多线程的编译环境中,unprotected sqlite3_value 对象只有被sqlite3_bind_value与sqlite3_result_value使用才是安全的。如果被像sqlite3_value_int,sqlite3_value_text,sqlite3_value_byte等调用,这是不安全的线程行为。
Internal Type |
Requested Type |
Conversion |
---|---|---|
NULL | INTEGER | Result is 0 |
NULL | FLOAT | Result is 0.0 |
NULL | TEXT | Result is a NULL pointer |
NULL | BLOB | Result is a NULL pointer |
INTEGER | FLOAT | Convert from integer to float |
INTEGER | TEXT | ASCII rendering of the integer |
INTEGER | BLOB | Same as INTEGER->TEXT |
FLOAT | INTEGER | CASTto INTEGER |
FLOAT | TEXT | ASCII rendering of the float |
FLOAT | BLOB | CASTto BLOB |
TEXT | INTEGER | CASTto INTEGER |
TEXT | FLOAT | CASTto REAL |
TEXT | BLOB | No change |
BLOB | INTEGER | CASTto INTEGER |
BLOB | FLOAT | CASTto REAL |
BLOB | TEXT | Add a zero terminator if needed |
特别指出:当发生类型转换时,可能导致上一级调用返回的指针,如sqlite3_column_blob(),sqlite3_column_text(),sqlite3_column_text16() 为无效。这种情况可能发生在下面几个case中:
- content类型为BLOB,调用sqlite3_column_text() orsqlite3_column_text16(),------可能会在字符串结尾加上‘\0’终止符。
- content类型为UTF-8 text,调用sqlite3_column_bytes16() orsqlite3_column_text16()。------将content转换为UTF-16。
- content类型为UTF-16 text,调用sqlite3_column_bytes8() orsqlite3_column_text8()。------将content转换为UTF-8。
UTF-16到UTF-16le之间的转换时安全的。
几个安全的使用策略:
- 先sqlite3_column_text() ,之后 sqlite3_column_bytes()
- 先sqlite3_column_blob() ,之后 sqlite3_column_bytes()
- 先sqlite3_column_text16() ,之后sqlite3_column_bytes16()
换句话说,可以先调用sqlite3_column_text() ,sqlite3_column_blob() ,sqlite3_column_text16() ,得到你想要的格式的结果,之后调用sqlite3_column_bytes(),sqlite3_column_bytes(),sqlite3_column_bytes16() 来得到该结果的大小。
附录:英文字母和汉字在不同的编码集中所占的字节数对比
汉字 英文字母 编码
字节数 : 2 1 GB2312
字节数 : 2 1 GBK
字节数 : 2 1 GB18030
字节数 : 1 1 ISO-8859-1
字节数 : 3 1 UTF-8
字节数 : 4 4 UTF-16
字节数 : 2 2 UTF-16BE
字节数 : 2 2 UTF-16LE