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

Flutter本地JSON列表搜索功能失效,请求协助排查解决

问题排查与解决方案

你的搜索功能失效主要有以下几个核心问题,对应修复方案如下:

问题点梳理

  • 搜索结果未清空:每次输入搜索词时,searchedData没有被清空,旧结果持续累加导致数据混乱。
  • 未触发UI更新:搜索逻辑执行后未调用setState(),Flutter无法感知状态变化刷新列表。
  • 重复加载数据:FutureBuilder直接绑定_loadfile(),组件每次重建都会重复读取本地文件,浪费资源且易引发状态混乱。
  • 搜索无大小写兼容:直接使用contains匹配,大小写不一致时会匹配失败。
  • 空搜索未重置显示:搜索文本清空时,未切换回显示原始的mmaData列表。

修复步骤

  1. 初始化单次加载数据:在initState中调用_loadfile(),避免重复执行文件读取操作。
  2. 完善搜索逻辑:
    • 每次搜索前清空searchedData
    • 调用setState()触发UI更新
    • 统一转小写实现大小写不敏感搜索
    • 处理空搜索场景,重置显示原始数据
  3. 用状态变量管理加载状态:替换FutureBuilder的重复执行问题,通过_isLoading变量控制加载提示显示。

修复后的完整代码

import 'dart:convert';
import 'package:flutter/material.dart';
import 'package:shared_preferences/shared_preferences.dart';
import 'dart:io';
import './mmamodel.dart';

class ShowData extends StatefulWidget {
  static const routeName = '/showData';
  @override
  State<ShowData> createState() => _ShowDataState();
}

class _ShowDataState extends State<ShowData> {
  List<mmamodel> mmaData = <mmamodel>[];
  List<mmamodel> searchedData = <mmamodel>[];
  TextEditingController controller = TextEditingController();
  bool _isLoading = true; // 新增加载状态变量

  Future _loadfile() async {
    final prefs = await SharedPreferences.getInstance();
    final path = prefs.getString('path');
    if (path == null) {
      setState(() => _isLoading = false);
      return;
    }
    File file = File(path);
    final contents = await file.readAsString();
    var list = json.decode(contents) as List<dynamic>;
    setState(() {
      mmaData = list.map((e) => mmamodel.fromJson(e)).toList();
      _isLoading = false;
    });
  }

  @override
  void initState() {
    super.initState();
    _loadfile(); // 初始化时仅加载一次数据
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('MMALIST'),
      ),
      body: Column(
        children: [
          _searchBar(),
          _isLoading
              ? const Center(child: CircularProgressIndicator())
              : Expanded(
                  child: searchedData.isEmpty
                      ? ListView.builder(
                          itemCount: mmaData.length,
                          itemBuilder: (context, index) {
                            return Text(mmaData[index].product.toString());
                          },
                        )
                      : ListView.builder(
                          itemCount: searchedData.length,
                          itemBuilder: (context, index) {
                            return Text(searchedData[index].product.toString());
                          },
                        ),
                ),
        ],
      ),
    );
  }

  Widget _searchBar() {
    return Padding(
      padding: const EdgeInsets.all(8),
      child: TextFormField(
        controller: controller,
        decoration: const InputDecoration(hintText: 'Search by product'),
        onChanged: onSearchTextChanged,
      ),
    );
  }

  void onSearchTextChanged(String text) {
    setState(() {
      if (text.isEmpty) {
        searchedData.clear(); // 清空搜索结果,恢复显示原始数据
        return;
      }
      final lowerText = text.toLowerCase();
      searchedData = mmaData.where((item) {
        final productName = item.product?.toLowerCase() ?? '';
        return productName.contains(lowerText);
      }).toList();
    });
  }
}

额外优化建议

  • 代码中已处理product字段的空值判断,避免空指针异常;
  • 若数据量较大,可改用ListView.separated提升滚动性能,或添加防抖逻辑(延迟500ms再执行搜索)减少频繁状态更新。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.14 13:50:22