You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter中SharedPreferences获取布尔值始终返回true问题

问题分析与解决方案

核心问题

你所有的Person实例都共用了同一个SharedPreferences键"Person['Joined']"——只要有一个Person被设置为true,这个键的值就会被永久覆盖为true,后续不管数据库里新建的Person默认值是false,读取这个固定键得到的都是之前存的true。

解决步骤

1. 给每个Person分配唯一标识

确保你的Person数据库表有唯一字段(比如id),用这个字段生成专属的SharedPreferences键,避免不同实例互相干扰。

2. 修改首页的状态存储逻辑

把固定键改成带唯一标识的动态键:

Widget listItem({
  required Map Person,
}) {
  void savebool() async {
    SharedPreferences prefs = await SharedPreferences.getInstance();
    // 用Person的id生成专属键,替换成你实际的唯一字段名
    String uniqueKey = "person_${Person['id']}_joined";
    await prefs.setBool(uniqueKey, Person['Joined']);
    print(Person['Joined']);
  }

  return Slidable(
    startActionPane: ActionPane(
      motion: const BehindMotion(),
      extentRatio: 1 / 5,
      children: [
        SlidableAction(
          backgroundColor: Colors.blue,
          icon: Icons.add,
          label: 'Join',
          onPressed: (BuildContext context) {
            setState(() {
              Person['Joined'] = true;
            });
            savebool();
          },
        )
      ],
    ),
    // 其他代码...
  );
}

3. 修改Favourites.dart的状态读取逻辑

需要把当前Person的唯一标识传到Favourites页面,然后读取对应键的值:

// 先给Favourites页面添加Person参数
class Favourites extends StatefulWidget {
  final Map Person;
  const Favourites({super.key, required this.Person});

  @override
  State<Favourites> createState() => _FavouritesState();
}

class _FavouritesState extends State<Favourites> {
  late bool joined;

  @override
  void initState() {
    super.initState();
    getPrefs();
  }

  getPrefs() async {
    SharedPreferences prefs = await SharedPreferences.getInstance();
    String uniqueKey = "person_${widget.Person['id']}_joined";
    setState(() {
      // 优先取本地存储的值,没有则用数据库默认值
      joined = prefs.getBool(uniqueKey) ?? widget.Person['Joined'];
      print("getbool: $joined");
    });
  }

  // 其他代码...
}

4. 列表项初始化时同步本地状态

在首页的列表项初始化时,要从对应键读取状态覆盖数据库默认值,保证显示和本地存储一致:

// 如果listItem是StatefulWidget,在initState里加载状态
@override
void initState() {
  super.initState();
  _loadJoinedState();
}

void _loadJoinedState() async {
  SharedPreferences prefs = await SharedPreferences.getInstance();
  String uniqueKey = "person_${widget.Person['id']}_joined";
  setState(() {
    widget.Person['Joined'] = prefs.getBool(uniqueKey) ?? widget.Person['Joined'];
  });
}

总结

通过给每个Person生成唯一的存储键,彻底解决了不同实例状态互相覆盖的问题。新创建的Person因为对应键不存在,会使用数据库默认的false值,不会再被旧的true值影响。

内容的提问来源于stack exchange,提问作者Tyrone

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.28 00:07:40