Flutter SharedPreferences 本地存储详解

Flutter SharedPreferences 本地存储详解 Flutter SharedPreferences 本地存储详解一、SharedPreferences 概述SharedPreferences 是一种轻量级的本地存储方案用于存储键值对数据。它适用于存储少量配置信息、用户偏好设置等简单数据。1.1 特点轻量级适合存储少量数据基于 XML 文件存储支持基本数据类型int、double、bool、String、List数据持久化存储1.2 添加依赖dependencies: shared_preferences: ^2.2.2二、基本用法2.1 初始化import package:shared_preferences/shared_preferences.dart; Futurevoid initPrefs() async { final prefs await SharedPreferences.getInstance(); // 使用 prefs 进行存储操作 }2.2 存储数据final prefs await SharedPreferences.getInstance(); // 存储字符串 await prefs.setString(username, John); // 存储整数 await prefs.setInt(age, 25); // 存储布尔值 await prefs.setBool(isDarkMode, true); // 存储浮点数 await prefs.setDouble(score, 95.5); // 存储字符串列表 await prefs.setStringList(favoriteColors, [red, blue, green]);2.3 读取数据final prefs await SharedPreferences.getInstance(); // 读取字符串默认值为 String? username prefs.getString(username); // 读取整数默认值为 0 int age prefs.getInt(age) ?? 0; // 读取布尔值默认值为 false bool isDarkMode prefs.getBool(isDarkMode) ?? false; // 读取浮点数默认值为 0.0 double score prefs.getDouble(score) ?? 0.0; // 读取字符串列表默认值为空列表 ListString favoriteColors prefs.getStringList(favoriteColors) ?? [];2.4 删除数据final prefs await SharedPreferences.getInstance(); // 删除单个键 await prefs.remove(username); // 清除所有数据 await prefs.clear();2.5 检查键是否存在final prefs await SharedPreferences.getInstance(); bool hasUsername prefs.containsKey(username);三、封装工具类3.1 创建存储服务import package:shared_preferences/shared_preferences.dart; class StorageService { static late SharedPreferences _prefs; static Futurevoid init() async { _prefs await SharedPreferences.getInstance(); } static String? getString(String key) { return _prefs.getString(key); } static Futurebool setString(String key, String value) { return _prefs.setString(key, value); } static int? getInt(String key) { return _prefs.getInt(key); } static Futurebool setInt(String key, int value) { return _prefs.setInt(key, value); } static bool? getBool(String key) { return _prefs.getBool(key); } static Futurebool setBool(String key, bool value) { return _prefs.setBool(key, value); } static double? getDouble(String key) { return _prefs.getDouble(key); } static Futurebool setDouble(String key, double value) { return _prefs.setDouble(key, value); } static ListString? getStringList(String key) { return _prefs.getStringList(key); } static Futurebool setStringList(String key, ListString value) { return _prefs.setStringList(key, value); } static bool containsKey(String key) { return _prefs.containsKey(key); } static Futurebool remove(String key) { return _prefs.remove(key); } static Futurebool clear() { return _prefs.clear(); } }3.2 在 main 函数中初始化void main() async { WidgetsFlutterBinding.ensureInitialized(); await StorageService.init(); runApp(const MyApp()); }四、实战案例用户设置管理4.1 创建设置模型class UserSettings { final String themeMode; final String language; final bool notificationsEnabled; final int fontSize; const UserSettings({ required this.themeMode, required this.language, required this.notificationsEnabled, required this.fontSize, }); // 从存储读取 static UserSettings fromStorage() { return UserSettings( themeMode: StorageService.getString(themeMode) ?? light, language: StorageService.getString(language) ?? zh, notificationsEnabled: StorageService.getBool(notificationsEnabled) ?? true, fontSize: StorageService.getInt(fontSize) ?? 16, ); } // 保存到存储 Futurevoid save() async { await StorageService.setString(themeMode, themeMode); await StorageService.setString(language, language); await StorageService.setBool(notificationsEnabled, notificationsEnabled); await StorageService.setInt(fontSize, fontSize); } }4.2 使用设置模型class SettingsPage extends StatelessWidget { const SettingsPage({super.key}); override Widget build(BuildContext context) { final settings UserSettings.fromStorage(); return Scaffold( appBar: AppBar(title: const Text(设置)), body: ListView( children: [ ListTile( title: const Text(主题模式), subtitle: Text(settings.themeMode), onTap: () async { final newSettings UserSettings( themeMode: dark, language: settings.language, notificationsEnabled: settings.notificationsEnabled, fontSize: settings.fontSize, ); await newSettings.save(); }, ), // 更多设置项... ], ), ); } }五、高级用法5.1 存储复杂对象虽然 SharedPreferences 只支持基本类型但可以通过 JSON 序列化存储复杂对象import dart:convert; class User { final String id; final String name; final int age; User({required this.id, required this.name, required this.age}); MapString, dynamic toJson() { return { id: id, name: name, age: age, }; } factory User.fromJson(MapString, dynamic json) { return User( id: json[id], name: json[name], age: json[age], ); } } // 存储 final user User(id: 1, name: John, age: 25); final userJson jsonEncode(user.toJson()); await StorageService.setString(user, userJson); // 读取 final userJson StorageService.getString(user); if (userJson ! null) { final user User.fromJson(jsonDecode(userJson)); }5.2 监听数据变化class SettingsProvider extends ChangeNotifier { UserSettings _settings UserSettings.fromStorage(); UserSettings get settings _settings; Futurevoid updateThemeMode(String themeMode) async { _settings UserSettings( themeMode: themeMode, language: _settings.language, notificationsEnabled: _settings.notificationsEnabled, fontSize: _settings.fontSize, ); await _settings.save(); notifyListeners(); } }六、注意事项6.1 数据类型限制SharedPreferences 只支持以下数据类型intdoubleboolStringListString6.2 数据大小限制建议存储的数据不超过 1MB大量数据应使用数据库如 Hive、SQFlite。6.3 异步操作所有写入操作都是异步的需要使用await等待完成。6.4 数据清理卸载应用时SharedPreferences 数据会被清除。七、与其他存储方案对比方案适用场景优点缺点SharedPreferences配置信息、用户偏好轻量级、使用简单数据类型有限、容量小Hive中等数据量、复杂对象支持自定义对象、速度快需要学习成本SQFlite大量数据、复杂查询支持 SQL、数据量大使用复杂、学习成本高File文件存储灵活、适合二进制数据需要手动管理八、实战案例登录状态管理class AuthService { static const String _keyIsLoggedIn isLoggedIn; static const String _keyUserId userId; static const String _keyToken token; static Futurebool isLoggedIn() async { final prefs await SharedPreferences.getInstance(); return prefs.getBool(_keyIsLoggedIn) ?? false; } static Futurevoid login(String userId, String token) async { final prefs await SharedPreferences.getInstance(); await prefs.setBool(_keyIsLoggedIn, true); await prefs.setString(_keyUserId, userId); await prefs.setString(_keyToken, token); } static Futurevoid logout() async { final prefs await SharedPreferences.getInstance(); await prefs.setBool(_keyIsLoggedIn, false); await prefs.remove(_keyUserId); await prefs.remove(_keyToken); } static FutureString? getToken() async { final prefs await SharedPreferences.getInstance(); return prefs.getString(_keyToken); } }九、测试9.1 单元测试import package:shared_preferences/shared_preferences.dart; import package:test/test.dart; void main() { group(StorageService, () { late SharedPreferences prefs; setUp(() async { prefs await SharedPreferences.getInstance(); await prefs.clear(); }); test(set and get string, () async { await prefs.setString(key, value); expect(prefs.getString(key), value); }); test(set and get int, () async { await prefs.setInt(count, 42); expect(prefs.getInt(count), 42); }); test(remove key, () async { await prefs.setString(key, value); expect(prefs.containsKey(key), true); await prefs.remove(key); expect(prefs.containsKey(key), false); }); }); }十、总结SharedPreferences 是 Flutter 中最简单的本地存储方案适用场景- 存储配置信息、用户偏好设置、简单状态优点- 使用简单、轻量级、异步操作局限性- 数据类型有限、容量较小最佳实践- 封装成工具类、配合 Provider 管理状态对于更复杂的存储需求可以考虑 Hive 或 SQFlite。