在 iOS 11 中,如果您将 sqlite3_column_name
与带有 subselect 语句的 SQL 一起使用,它现在会返回带有表前缀的列名,而 iOS 10 则不会。
例如考虑这个 SQL:
SELECT f.foo_value, b.bar_value
FROM foo as f LEFT JOIN
(SELECT * FROM bar) AS b ON f.foo_id = b.foo_id
如果您随后使用 sqlite3_column_name
检索列名(注意这是 Objective-C 片段,但这是一个 SQLite 问题,并非 Objective-C 或 Swift 独有):
const char *name1 = sqlite3_column_name(statement, 0);
const char *name2 = sqlite3_column_name(statement, 1);
NSLog(@"SQLite version: %s", sqlite3_version);
NSLog(@"name of column 0: %s", name1);
NSLog(@"name of column 1: %s", name2);
在 iOS 11.1 中,此报告:
SQLite version: 3.19.3
name of column 0: f.foo_value
name of column 1: b.bar_value
在 iOS 10.1 中,此报告:
SQLite version: 3.14.0
name of column 0: foo_value
name of column 1: bar_value
为什么?
顺便说一句,这个问题似乎只在 SQL 包含子选择语句时才会出现。
最佳答案
作为 SQLite documentation for sqlite3_column_name
说:
The name of a result column is the value of the "AS" clause for that column, if there is an AS clause. If there is no AS clause then the name of the column is unspecified and may change from one release of SQLite to the next.
所以,如果你想将 sqlite3_column_name
的结果用于信息以外的任何目的,你真的应该在你的 SQL 中使用 AS
子句,例如
SELECT f.foo_value AS foo_value, b.bar_value AS bar_value
FROM ...
作为Gwendal Roué noted ,这是 iOS 11 附带的 SQLite 版本中引入的一个已知问题:
This change has been introduced in SQLite 3.19.0. It is present in SQLite 3.19.3 shipped with iOS 11. It has been reverted in SQLite 3.20.0.
For more information, see:
- Ticket: https://sqlite.org/src/info/de3403bf5ae5f72ed
- Mailing-list: http://mailinglists.sqlite.org/cgi-bin/mailman/private/sqlite-users/2017-July/073955.html
- SQLite 3.20.0 release notes: https://sqlite.org/changes.html#version_3_20_0
关于ios - 带有 subselect 语句的 SQL 的 SQLite 列名现在以表名作为列名的前缀,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47142644/