非常教程

Sqlite参考手册

其他 | Miscellaneous

SQLite As An Application File Format

Executive Summary

具有定义模式的SQLite数据库文件通常会提供出色的应用程序文件格式。这里有十几个理由:

  • 简化的应用开发
  • 单文件文件
  • 高级查询语言
  • 无障碍内容
  • 跨平台
  • 原子交易
  • 增量和连续更新
  • 易于扩展
  • 性能
  • 多进程并发使用
  • 多种编程语言
  • 更好的应用

在首先更仔细地考虑“应用程序文件格式”的含义之后,将在下面更详细地描述这些点中的每一个。另请参阅此白皮书的简短版本。

What Is An Application File Format?

“应用程序文件格式”是用于将应用程序状态持久化到磁盘或在程序之间交换信息的文件格式。目前有数千种应用程序文件格式正在使用。这里只是一些例子:

  • DOC - Word Perfect和Microsoft Office文档
  • DWG - AutoCAD图纸
  • PDF - Adob​​e公司的可移植文档格式
  • XLS - Microsoft Excel电子表格
  • GIT - Git源代码库
  • EPUB - 非Kindle电子书使用的电子出版格式
  • ODT - OpenOffice和其他人使用的Open Document格式
  • PPT - Microsoft PowerPoint演示文稿
  • ODP - OpenOffice和其他人使用的Open Document演示文稿格式

我们区分“文件格式”和“应用程序格式”。文件格式用于存储单个对象。因此,例如,GIF或JPEG文件存储单个图像,而XHTML文件存储文本,因此这些文件是“文件格式”而不是“应用程序格式”。相反,EPUB文件存储文本和图像(包含XHTML和GIF / JPEG文件),所以它被认为是“应用程序格式”。这篇文章是关于“应用程序格式”。

文件格式和应用程序格式之间的界限是模糊的。本文称JPEG为文件格式,但对于图像编辑器,JPEG可能被认为是应用程序格式。这很大程度上取决于上下文。对于本文,让我们说一个文件格式存储单个对象,应用程序格式存储许多不同的对象及其相互之间的关系。

大多数应用程序格式都符合以下三个类别之一:

  • 完全自定义格式。自定义格式是专门为单个应用程序设计的。DOC,DWG,PDF,XLS和PPT是自定义格式的示例。自定义格式通常包含在单个文件中,以便于传输。它们通常也是二进制的,尽管DWG格式是一个明显的例外。自定义文件格式需要专门的应用程序代码才能读取和写入,并且通常无法从常用工具(如unix命令行程序和文本编辑器)访问。换句话说,自定义格式通常是“不透明的斑点”。要访问自定义应用程序文件格式的内容,需要专门设计用于读取和/或写入该格式的工具。
  • 堆文件格式。有时应用程序状态被存储为文件的层次结构。Git就是一个很好的例子,尽管这种现象经常发生在一次性和定制的应用程序中。一堆文件格式基本上使用文件系统作为键/值数据库,将小块信息存储到单独的文件中。这提供了使内容更易于访问诸如文本编辑器或“awk”或“grep”等常用实用程序的优点。但即使堆文件格式中的许多文件易于阅读,通常也有一些文件具有自己的自定义格式(例如:Git“Packfiles”),因此是“不透明的斑点”,不可读或不可读无需专门工具即可写入。把一堆文件从一个地方或一台机器搬到另一个地方或机器上也不太方便,比移动单个文件要多。例如,很难在电子邮件附件中生成一堆文件。最后,一堆文件格式打破了“文档隐喻”:没有一个用户可以指向的文件就是“文档”。
  • 包裹的文件夹格式。一些应用程序使用一堆文件,然后将其封装到某种单文件容器中,通常是一个ZIP压缩文件。EPUB,ODT和ODP就是这种方法的例子。一本EPUB书籍实际上只是一个ZIP存档,其中包含用于书籍章节文本的各种XHTML文件,用于该艺术品的GIF和JPEG图像,以及一个专门的目录文件,告诉电子书阅读器如何将所有XML和图像文件放在一起。OpenOffice文档(ODT和ODP)也是ZIP档案,其中包含表示其内容的XML和图像以及显示组成部分之间相互关系的“目录”文件。

一个包裹的一堆文件格式是一个完整的自定义文件格式和纯文件堆栈格式之间的折中。由于组件部分仍然可以使用任何常用ZIP归档程序访问,所以包装的一堆文件格式不是一个不透明的blob,因为该组件部分仍然可以使用任何常用ZIP归档程序访问,但格式不像纯粹的一堆-files格式,因为仍然需要ZIP存档器,而且通常不使用命令行工具(如文件层次结构中的“find”),而无需先解压缩它。另一方面,一个包裹的文件堆栈格式通过将所有内容放入单个磁盘文件来保留文档隐喻。而且由于它是压缩的,所以包裹的一堆文件格式往往更加紧凑。

与自定义文件格式一样,与纯粹的文件堆栈格式不同,一个包裹的一堆文件格式不容易编辑,因为通常必须重写整个文件以更改任何组件部分。

本文档的目的是争论第四类新的应用程序文件格式:一个SQLite数据库文件。

SQLite As The Application File Format

任何可以记录在一堆文件中的应用程序状态也可以通过一个简单的键/值模式记录在SQLite数据库中,如下所示:

CREATE TABLE files(filename TEXT PRIMARY KEY, content BLOB);

如果内容被压缩,那么这样一个SQLite数据库与等效ZIP压缩文件大小相同(±1%),并且它的优点是能够在不重写整个文档的情况下更新单个“文件”。

但是SQLite数据库并不局限于一堆简单的键/值结构,比如一堆文件数据库。一个SQLite数据库可以有数十或数百或数千个不同的表,每个表有数十或数百或数千个字段,每个字段都有不同的数据类型和约束以及特定的含义,所有这些都相互交叉引用,适当且自动地索引以便快速检索,并全部高效且紧凑地存储在单个磁盘文件中。所有这些结构都是通过SQL模式为人类简洁地记录下来的。

换句话说,一个SQLite数据库可以完成一堆文件或者一堆文件格式可以做的所有事情,再加上更多,并且更加清晰。SQLite数据库是比键/值文件系统或ZIP归档更通用的容器。(有关详细示例,请参阅OpenOffice案例研究文章。)

理论上,SQLite数据库的强大功能可以使用自定义文件格式来实现。但是任何与关系数据库一样具有表现力的自定义文件格式可能需要巨大的设计规范和数十或数十万行代码才能实现。最终的结果将是一个“不透明的斑点”,如果没有专门的工具就无法进入。

因此,与其他方法相比,使用SQLite数据库作为应用程序文件格式具有显着的优势。列举并阐述了以下几个优点:

  • 简化的应用开发。读取或写入应用程序文件不需要新的代码。一个只需要链接到SQLite库,或者将单个“sqlite3.c”源文件与其余的应用程序C代码一起包含,SQLite将负责所有的应用程序文件I / O。这可以将应用程序代码大小减少数千行,相应地节省了开发和维护成本。SQLite是世界上使用最多的软件库之一。实际上,每天在智能手机和小工具以及桌面应用程序中使用数百亿SQLite数据库文件。SQLite经过仔细测试并证明可靠。它不是一个需要大量调优或调试的组件,允许开发人员专注于应用程序逻辑。
  • 单文件文件。SQLite数据库包含在单个文件中,该文件很容易复制,移动或附加。“文件”隐喻被保留下来。

SQLite没有任何文件命名要求,因此应用程序可以使用任何自定义文件后缀来帮助将文件标识为“属于”应用程序。SQLite数据库文件的头文件中包含一个4字节的应用程序ID,可以将其设置为应用程序定义的值,然后用于标识实用程序(如文件(1))的文档“类型” ,进一步增强文档隐喻。

  • 高级查询语言。SQLite是一个完整的关系数据库引擎,这意味着应用程序可以使用高级查询访问内容。应用程序开发人员不需要花时间思考如何从文档中检索他们所需的信息。开发人员编写表达他们想要的“什么”信息的SQL,让数据库引擎找出如何最好地检索该内容。这有助于开发人员“正面向上”运作,并继续专注于解决用户的问题,并避免花费时间“低头”摆弄低级文件格式细节。一堆文件格式可以被视为一个键/值数据库。键/值数据库根本比没有数据库好。但没有交易或索引或高级查询语言或适当的模式,
  • 无障碍内容。保存在SQLite数据库文件中的信息可以使用常用的开源命令行工具 - 默认情况下安装在Mac和Linux系统上的工具访问,并且可以在Windows上作为自包含的EXE文件免费使用。与自定义文件格式不同,应用程序特定的程序不需要读取或写入SQLite数据库中的内容。SQLite数据库文件不是不透明的blob。确实,命令行工具(如文本编辑器或“grep”或“awk”)在SQLite数据库上没有用处,但SQL查询语言是检查内容的更强大和更方便的方式,因此无法使用“grep”和“awk”等并不被视为损失。

SQLite数据库是一个定义明确且记录良好的文件格式,它被数百万个应用程序广泛使用,并且在2004年开始向后兼容,并且在接下来的几十年内将保持持续兼容。SQLite数据库文件的寿命对于定制的应用程序尤其重要,因为它允许在将来丢失文档内容的很长时间后访问文档内容。数据寿命比代码长。

  • 跨平台的。SQLite数据库文件可以在32位和64位计算机之间以及大端和小端体系结构之间以及任何类型的Windows和类Unix操作系统之间移植。使用SQLite应用程序文件格式的应用程序可以存储二进制数字数据,而不必担心整数或浮点数的字节顺序。文本内容可以读写为UTF-8,UTF-16LE或UTF-16BE,SQLite将自动执行任何必要的翻译。
  • 原子交易。写入SQLite数据库是原子的。它们要么完全发生,要么根本不发生,即使在系统崩溃或电力故障期间也是如此。所以,没有任何文件被破坏的危险,仅仅是因为在写入到磁盘上的同一时刻电源发生了故障。

SQLite是事务性的,这意味着可以将多个更改组合在一起,以使其全部或全部不发生,并且如果在提交之前发现问题则可以回滚更改。这允许应用程序逐步进行更改,然后在将更改提交到磁盘之前对结果数据运行各种完整性和一致性检查。该化石 DVCS 使用这种技术来验证没有仓库的历史前已经向每一个变化丢失。

  • 增量和连续更新。在写入SQLite数据库文件时,只有实际更改的那部分文件才写入磁盘。这使得写作更快速并且可以节省SSD的磨损。与自定义和包装文件堆栈格式相比,这是一个巨大的优势,它们通常需要重写整个文档才能更改单个字节。纯堆文件格式也可以在一定程度上进行增量更新,尽管通过堆栈文件格式(单个文件)的写入粒度通常比使用SQLite(单个页面)更大。SQLite也支持持续更新。除了在内存中收集更改,然后仅在文件/保存操作中将它们写入磁盘,更改可以在发生时写回到磁盘。这避免了在系统崩溃或电力故障时丢失工作。一个自动撤消/重做堆栈,
  • 易于扩展。随着应用程序的增长,只需​​向模式添加新表格或向现有表格添加新列,即可将新功能添加到SQLite应用程序文件格式中。添加列或表并不会改变先前查询的含义,因此,为了确保遗留列和表的含义得到保留,需要小心谨慎地维护向后兼容性。

当然,也可以扩展定制或堆积文件格式,但这样做通常要困难得多。如果添加了索引,则必须定位和修改更改相应表的所有应用程序代码,以使这些索引保持最新。如果添加了列,那么访问相应表的所有应用程序代码都必须进行定位和修改,以考虑新列。

  • 性能。在许多情况下,SQLite应用程序文件格式将比堆叠文件格式或自定义格式更快。除了原始读取和写入速度更快外,SQLite通常可以显着缩短启动时间,因为不必将整个文档读取并分析到内存中,应用程序可以执行查询以仅提取初始屏幕所需的信息。随着应用程序的不断发展,它只需要加载绘制下一个屏幕所需的材料,并且可以丢弃之前不再使用的屏幕中的信息。这有助于控制应用程序的内存占用。一堆文件格式可以像SQLite一样逐步读取。但是很多开发人员都惊讶地发现,SQLite可以从其数据库中读取和写入更小的BLOB(大小小于约100KB),这些BLOB可以更快地读取或写入文件系统中的单独文件。(有关详细信息,请参阅文件系统和内部与外部BLOB的比35%更快)。与操作关系数据库引擎相关的开销,但不应假定直接文件I / O比SQLite数据库I / O更快,因为通常情况并非如此。无论哪种情况,如果SQLite应用程序中出现性能问题,那么这些问题通常可以通过向模式添加一个或两个CREATE INDEX语句或者可能一次运行ANALYZE来解决,而不必触摸单行应用程序代码。但是,如果性能问题出现在自定义或堆叠文件格式中,
  • 多进程并发使用。SQLite自动协调对来自多个线程和/或进程的同一文档的并发访问。两个或多个应用程序可以同时连接和读取同一文档。写入是序列化的,但由于写入通常只需要几毫秒,应用程序只需轮流写入。SQLite自动确保文档的低级格式不被破坏。相比之下,使用自定义文件格式或堆积文件格式来实现这一点,则需要在应用程序中提供广泛的支持。而支持并发所需的应用程序逻辑是臭名昭着的bug磁铁。
  • 多种编程语言。虽然SQLite本身是用ANSI-C编写的,但是你可以想到的几乎所有其他编程语言都存在接口:C ++,C#,Objective-C,Java,Tcl,Perl,Python,Ruby,Erlang,JavaScript等等。所以程序员可以用任何他们最喜欢的语言进行开发,并且最适合项目的需求。

SQLite应用程序文件格式是单独程序的集合或“联合”情况下的最佳选择,通常用不同的语言和不同的开发团队编写。这通常出现在研究或实验室环境中,其中一个团队负责数据采集,而其他团队负责不同阶段的分析。每个团队都可以使用他们最喜欢的任何硬件,操作系统,编程语言和开发方法,只要所有程序使用具有通用模式的SQLite数据库,它们都可以互操作。

  • 更好的应用。如果应用程序文件格式是SQLite数据库,则该文件格式的完整文档由数据库模式组成,可能还有一些关于每个表格和列代表的内容。另一方面,自定义文件格式的描述通常运行数百页。一堆文件格式虽然比完全自定义格式更简单,更容易描述,但仍然比SQL模式转储更大更复杂,因为仍然需要描述单个文件的名称和格式。

这不是一个小问题。清晰,简明,易于理解的文件格式是任何应用程序设计的关键部分。弗雷德布鲁克斯,在他的畅销的计算机科学文本,The Mythical Man-Month 记载:

表示是计算机编程的本质。

...

展示你的流程图并隐藏你的表格,我会继续迷惑。给我看你的表格,我通常不需要你的流程图; 他们会很明显。

Rob Pike在他的规则规则中表达了同样的想法:

数据占主导地位。如果你选择了正确的数据结构并且组织得很好,算法几乎总是不言而喻的。数据结构,而不是算法,是编程的核心。

2006年6月27日,Linus Torvalds在Git邮件列表上用了不同的词语:

糟糕的程序员担心代码。好的程序员担心数据结构及其关系。

重点在于:SQL数据库模式几乎总是能够更好地定义和组织表和数据结构及其关系。清晰,简洁和明确的表示几乎总是会导致应用程序执行得更好,问题更少,开发和维护也更容易。

Conclusion

对于每种情况,SQLite都不是完美的应用程序文件格式。但是在很多情况下,SQLite比自定义文件格式,一堆文件或者一堆文件都要好得多。SQLite是一种高级,稳定,可靠,跨平台,广泛部署,可扩展,高性能,可访问的并发文件格式。它值得您考虑作为下一个应用程序设计的标准文件格式。

 SQLite is in the Public Domain.

其他 | Miscellaneous相关

1.35% Faster Than The Filesystem
2.8+3 Filenames
3.An Asynchronous I/O Module For SQLite
4.Appropriate Uses For SQLite
5.Architecture of SQLite
6.Atomic Commit In SQLite
7.Automatic Undo/Redo With SQLite
8.Benefits of SQLite As A File Format
9.Change in Default Page Size in SQLite Version 3.12.0
10.Clustered Indexes and the WITHOUT ROWID Optimization
11.Compile-time Options
12.Constraint Conflict Resolution in SQLite
13.Custom Builds Of SQLite
14.Deterministic SQL Functions
15.Distinctive Features Of SQLite
16.EXPLAIN QUERY PLAN
17.Features Of SQLite
18.File Format Changes in SQLite
19.Full-Featured SQL
20.High Reliability
21.Hints for Debugging SQLite
22.How SQLite Is Tested
23.How To Compile SQLite
24.How To Download Canonical SQLite Source Code
25.Imposter Tables
26.In-Memory Databases
27.Indexes On Expressions
28.Internal Versus External BLOBs
29.Isolation In SQLite
30.Long Term Support
31.Maintaining Private Branches Of SQLite
32.Many Small Queries Are Efficient In SQLite
33.Measuring and Reducing CPU Usage in SQLite
34.Memory-Mapped I/O
35.NULL Handling in SQLite
36.Partial Indexes
37.Pointer Passing Interfaces
38.Powersafe Overwrite
39.Release History Of SQLite
40.Result and Error Codes
41.Row Values
42.Rowid Tables
43.Run-Time Loadable Extensions
44.SQL Features That SQLite Does Not Implement
45.sqldiff.exe: Database Difference Utility
46.SQLite Autoincrement
47.SQLite Backup API
48.SQLite Changes From Version 3.4.2 To 3.5.0
49.SQLite Changes From Version 3.5.9 To 3.6.0
50.SQLite Database Speed Comparison
51.SQLite File IO Specification
52.SQLite Frequently Asked Questions
53.SQLite In 5 Minutes Or Less
54.SQLite is a Self Contained System
55.SQLite Is Serverless
56.SQLite Is Transactional
57.SQLite Library Footprint
58.SQLite Shared-Cache Mode
59.SQLite Unlock-Notify API
60.SQLite Version 3 Overview
61.SQLite: Single File Database
62.Temporary Files Used By SQLite
63.TH3
64.The COMPLETION() Table-Valued Function
65.The CSV Virtual Table
66.The dbhash.exe Utility Program
67.The DBSTAT Virtual Table
68.The Error And Warning Log
69.The generate_series Table-Valued Function
70.The OS Backend (VFS) To SQLite
71.The Spellfix1 Virtual Table
72.The SQLite Amalgamation
73.The SQLite Bytecode Engine
74.The sqlite3_analyzer.exe Utility Program
75.The SQLITE_STMT Virtual Table
76.The UNION Virtual Table
77.The Virtual Database Engine of SQLite
78.Uniform Resource Identifiers
79.Using SQLite In Multi-Threaded Applications
80.Version Numbers in SQLite
81.What If OpenDocument Used SQLite?
82.Why Is SQLite Coded In C
83.Zero-Configuration
Sqlite

SQLite,是一款轻型的数据库,是遵守ACID的关系型数据库管理系统,它包含在一个相对小的C库中。它是D.RichardHipp建立的公有领域项目。它的设计目标是嵌入式的,而且目前已经在很多嵌入式产品中使用了它,它占用资源非常的低,在嵌入式设备中,可能只需要几百K的内存就够了。它能够支持Windows/Linux/Unix等等主流的操作系统,同时能够跟很多程序语言相结合,比如 Tcl、C#、PHP、Java等,还有ODBC接口,同样比起Mysql、PostgreSQL这两款开源的世界著名数据库管理系统来

主页 https://sqlite.org/
源码 https://www.sqlite.org/src/
发布版本 3.21.0

Sqlite目录

1.C界面 | C Interface
2.C Interface: Session Module
3.CLI
4.数据库文件表 | Database File Format
5.数据类 | Datatypes
6.动态内存分配 | Dynamic Memory Allocation
7.外键约束 | Foreign Key Constraints
8.全文索引 | Full-Text Search
9.损坏方式 | How To Corrupt
10.JSON
11.语言 | Language
12.局限性 | Limits
13.锁定和并发 | Locking and Concurrency
14.其他 | Miscellaneous
15.PRAGMA Statements
16.查询计划程序 | Query Planner
17.R*Tree Module
18.RBU Extension
19.语法图 | Syntax Diagrams
20.Tcl Interface
21.虚拟表机制 | Virtual Table Mechanism
22.预写日志 | Write-Ahead Logging
23.SQL 教程
24.SQL 简介
25.SQL 语法
26.SQL DELETE 语句
27.SQL UPDATE 语句
28.SQL NOT NULL 约束
29.SQL 约束
30.SQL CREATE TABLE 语句
31.SQL CREATE DATABASE 语句
32.SQL INSERT INTO SELECT 语句
33.SQL SELECT INTO 语句
34.SQL CREATE VIEW、REPLACE VIEW、 DROP VIEW 语句
35.SQL AUTO INCREMENT 字段
36.SQL ALTER TABLE 语句
37.SQL 撤销索引、表以及数据库
38.SQL CREATE INDEX 语句
39.SQL DEFAULT 约束
40.SQL CHECK 约束
41.SQL FOREIGN KEY 约束
42.SQL PRIMARY KEY 约束
43.SQL UNIQUE 约束
44.SQL 通用数据类型
45.SQL ISNULL()、NVL()、IFNULL() 和 COALESCE() 函数
46.SQL NULL 值 – IS NULL 和 IS NOT NULL
47.SQL Server 和 MySQL 中的 Date 函数
48.SQL MS Access、MySQL 和 SQL Server 数据类型
49.SQL 函数
50.SQL 总结
51.SQL 主机
52.SQL 快速参考
53.SQL ROUND() 函数
54.SQL Server GETDATE() 函数
55.MySQL DATE_FORMAT() 函数
56.MySQL DATEDIFF() 函数
57.MySQL DATE_SUB() 函数
58.MySQL DATE_ADD() 函数
59.MySQL EXTRACT() 函数
60.MySQL DATE() 函数
61.MySQL CURTIME() 函数
62.MySQL CURDATE() 函数
63.MySQL NOW() 函数
64.SQL Server CONVERT() 函数
65.SQL Server DATEDIFF() 函数
66.SQL Server DATEADD() 函数
67.SQL Server DATEPART() 函数
68.SQLite 命令
69.SQLite 安装
70.SQLite 简介
71.SQLite 运算符
72.SQLite Select 语句
73.SQLite 删除表
74.SQLite 创建表
75.SQLite Insert 语句
76.SQLite 分离数据库
77.SQLite 附加数据库
78.SQLite 创建数据库
79.SQLite 数据类型
80.SQLite 语法
81.SQLite Order By
82.SQLite Limit 子句
83.SQLite Glob 子句
84.SQLite Like 子句
85.SQLite Delete 语句
86.SQLite Update 语句
87.SQLite AND/OR 运算符
88.SQLite Where 子句
89.SQLite 表达式
90.SQLite Distinct 关键字
91.SQLite Having 子句
92.SQLite Group By
93.SQLite Join
94.SQLite 约束
95.SQLite PRAGMA
96.SQLite 事务
97.SQLite 视图
98.SQLite Truncate Table
99.SQLite Alter 命令
100.SQLite Indexed By