在阅读https://sqlite.org/datatype3.html后,其中声明
“SQLite没有专门用于存储日期和/或时间的存储类。”
但能够运行这个
CREATE TABLE User (ID INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, BORN_ON DATE NULL)
然后在“DB Browser for SQL”中看到它,如下所示:
我开始怀疑SQLite是否支持Date类型,它只是“假装”支持其他类型。即使如此,为什么DB浏览器将其视为Date?DB中存储了任何 meta信息吗?
4条答案
按热度按时间fcwjkofz1#
SQLite不会用
Numeric
s伪造Date
。SQLite中没有
Date
数据类型。在Datatypes In SQLite Version 3中,清楚地解释了:
SQLite使用更通用的动态类型系统
除了数据类型,还有5个存储类:
NULL
、INTEGER
、REAL
、TEXT
和BLOB
。还有:
SQLite第3版数据库中的任何列(INTEGER PRIMARY KEY列除外)都可用于存储任何存储类的值。
因此,当你在
CREATE TABLE
语句中使用Date
作为列的数据类型时,你并不局限于只能在其中存储类似日期的值。实际上,你可以在该列中存储任何东西。像“DBBrowserforSQLite”和其他工具可能提供各种数据类型供选择,以便在创建表时定义列。
您所做的数据类型的选择并不受限制,但它可以指示要在列中存储的数据类型。
实际上,您甚至可以在不声明列的数据类型的情况下创建表:
或者使用虚构的数据类型:
并插入任何数据类型的值:
e4yzc0pl2#
根据Colonel Thirty Two的建议(在页面上阅读更多内容),似乎当你将一个字段声明为Date时,它的亲和性将是数字。
所以SQLite用数字“伪造”了日期。
axr492tv3#
即使是这样,为什么数据库浏览器将其视为日期?数据库中存储的任何 meta信息?
是的,它只是存储了创建列时使用的类型名称。链接页面称之为“声明类型”。在这种情况下,您将获得
NUMERIC
亲和性(DATE
甚至在3.1.1中作为示例之一给出),它的行为与具有此亲和性的任何其他列一样:具有NUMERIC关联的列可能包含使用所有五个存储类的值。当文本数据插入NUMERIC列时,文本的存储类将转换为INTEGER或真实的如果TEXT值是一个格式良好的整数文字,但它太大,无法装入一个64位有符号整数,它被转换为真实的。对于TEXT和REAL存储类之间的转换,仅保留数字的前15个有效十进制数字。如果TEXT值不是格式良好的整数或实文字,则该值被存储为TEXT。出于本段的目的,十六进制整数文字不被认为是格式良好的,并且被存储为TEXT。(这是为了与版本3.8.6之前的SQLite版本保持历史兼容性2014-08-15十六进制整数文字首次引入SQLite。)如果将可以精确表示为整数的浮点值插入到具有NUMERIC亲和性的列中,则该值将转换为整数。不会尝试转换NULL或BLOB值。
一个字符串可能看起来像一个带有小数点和/或指数表示法的浮点文字,但只要该值可以表示为整数,NUMERIC亲和性就会将其转换为整数。因此,字符串'3.0e+5'在具有NUMERIC亲和性的列中存储为整数300000,而不是浮点值300000.0。
因此,如果您插入的日期看起来像
"2021-01-05"
,它们将被存储为字符串。1.你也可以插入不像日期的字符串。
1.如果你插入
"20210105"
,它将被存储为数字20210105
。您可以使用
CHECK
约束来防止插入非日期字符串。另请参阅https://sqlite.org/lang_datefunc.html,它说明了日期/时间函数期望的格式(字符串和数字)。
wvyml7n54#
我在这里有一些关于SQLite日期的注解:https://internotes.net/sqlite-dates
这是简短的版本。
开始,SQLite不强制数据类型,它所做的是类型affinity,它基本上定义了在特定列中找到的任何内容的默认解释。
SQLite非常宽容,它可以接受任何类型的数据,你可以给它起一个类型名,它会接受,但是不要指望它知道你在说什么。
SQLite没有特定的日期类型关联。相反,你应该用途:
当然,它们仍然不是日期和时间,所以SQLite有很多函数来操作它们。
所以,简短的回答是否定的,没有
DATE
类型。如果你想以特定的方式存储和处理你的日期,你可以选择上面的类型亲和力之一。