SQLite数据库文件存储目录
- Android系统
- 对于Android应用使用的SQLite数据库,其数据库文件通常存储在应用的私有数据目录下,路径格式一般为
/data/data/<package_name>/databases/
。例如,一个包名为com.example.app
的应用,其SQLite数据库文件可能存放在/data/data/com.example.app/databases/
目录下。这个目录具有应用私有特性,其他应用没有权限直接访问,保证了数据的安全性。
- iOS系统
- 在iOS中,SQLite数据库文件常存放在应用的沙盒目录下。具体路径根据应用需求可以在
Documents
、Library
(包括Caches
和Preferences
等子目录)或者tmp
目录中。比如,若希望数据库文件能备份到iCloud,可以将其存放在Documents
目录;若不需要备份,可放在Caches
目录。Documents
目录路径一般为~/Documents
,Caches
目录路径为~/Library/Caches
。
- 桌面操作系统(以Windows为例)
- 在Windows应用中,SQLite数据库文件的存储位置由应用开发者决定。常见的是应用程序安装目录,或者用户特定的文件夹,如
%APPDATA%
目录。例如,应用可能将数据库文件存放在%APPDATA%\CompanyName\AppName\
目录下,这样可以利用系统对用户数据的管理机制,不同用户有各自独立的数据存储位置。
确保数据持久化和一致性
- SQLite事务机制
- 事务定义:SQLite通过事务(Transaction)来保证数据的一致性和完整性。一个事务是由一组SQL语句组成的逻辑单元,这些语句要么全部成功执行,要么全部不执行。
- 事务操作:
- 开始事务:在SQLite中,可以使用
BEGIN TRANSACTION;
语句开始一个事务。例如,在Java中使用SQLite时,可以这样写:
Connection conn = DriverManager.getConnection("jdbc:sqlite:test.db");
Statement stmt = conn.createStatement();
stmt.execute("BEGIN TRANSACTION;");
- **执行SQL语句**:在事务开始后,可以执行一系列的`INSERT`、`UPDATE`、`DELETE`等操作。例如:
stmt.execute("INSERT INTO users (name, age) VALUES ('John', 30);");
stmt.execute("UPDATE users SET age = 31 WHERE name = 'John';");
- **提交事务**:当所有操作完成且都成功时,使用`COMMIT;`语句提交事务,将所有修改持久化到数据库文件。例如:
stmt.execute("COMMIT;");
- **回滚事务**:如果在事务执行过程中出现错误,可以使用`ROLLBACK;`语句回滚事务,撤销事务中已执行的所有操作,使数据库回到事务开始前的状态。例如:
try {
// 开始事务
stmt.execute("BEGIN TRANSACTION;");
// 执行SQL语句
stmt.execute("INSERT INTO users (name, age) VALUES ('John', 30);");
// 模拟错误
stmt.execute("INVALID SQL STATEMENT;");
// 提交事务(不会执行到这里,因为前面有错误)
stmt.execute("COMMIT;");
} catch (SQLException e) {
// 回滚事务
stmt.execute("ROLLBACK;");
e.printStackTrace();
}
- 系统崩溃处理
- 预写式日志(WAL)模式:SQLite支持预写式日志(Write - Ahead Logging,WAL)模式。在WAL模式下,所有的修改先写入一个日志文件(
.wal
文件),而不是直接修改数据库文件。系统崩溃时,下次数据库启动时会检查WAL文件,将未完成的事务回滚,已完成的事务重新应用,从而保证数据一致性。可以通过PRAGMA journal_mode = WAL;
语句开启WAL模式。例如,在Python中使用SQLite时:
import sqlite3
conn = sqlite3.connect('test.db')
conn.execute('PRAGMA journal_mode = WAL;')
- 检查点机制:在WAL模式下,SQLite会定期执行检查点(Checkpoint)操作。检查点会将WAL日志文件中的已提交事务应用到数据库文件中,并截断WAL日志文件。这有助于减少系统崩溃后恢复所需的时间和资源。可以通过
PRAGMA wal_autocheckpoint = <value>;
来控制自动检查点的频率,<value>
为0时关闭自动检查点,1时每次事务提交都进行检查点操作,大于1的值表示每value
次事务提交进行一次检查点操作。例如:
conn.execute('PRAGMA wal_autocheckpoint = 10;')
- 同步机制:SQLite提供了不同级别的同步(Synchronous)设置,通过
PRAGMA synchronous = <value>;
语句设置。<value>
有三个取值:OFF
、NORMAL
、FULL
。OFF
模式下,写操作不等待数据真正写入磁盘,速度最快,但系统崩溃时可能丢失最新数据;NORMAL
模式下,写操作会等待数据写入磁盘缓存,能在大多数情况下保证数据不丢失;FULL
模式下,写操作会等待数据真正写入磁盘,安全性最高,但性能相对较低。例如:
conn.execute('PRAGMA synchronous = NORMAL;')