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

Flutter从数据库获取数据无法生成目标分组结构问题求助

问题与解决方案:从数据库构建日期分组的事件Map

问题说明

原本的loadPreviousEvents()函数生成的是以日期为键、事件列表为值的Map结构,示例如下:

loadPreviousEvents() {
  mySelectedEvents = {
    "2022-09-13": [
      {"eventDescp": "11", "eventTitle": "111"},
      {"eventDescp": "22", "eventTitle": "22"}
    ],
    "2022-09-30": [
      {"eventDescp": "22", "eventTitle": "22"}
    ],
    "2022-09-20": [
      {"eventTitle": "ss", "eventDescp": "ss"}
    ]
  };
  print(mySelectedEvents);
}

现在需要从数据库接口获取数据并转换成相同结构,但尝试的异步代码返回的是[Instance of 'Future<GroupBy>']类型的列表,无法得到目标Map。

尝试的代码

loadPreviousEvents() async {
  var url = 'http://prospection.global-aeit.com/getEvents.php';
  var res = await http.get(Uri.parse(url));
  var response = json.decode(res.body) as List;
  print(response);
  var mySelectedEvents =
      (response.map((e) async => GroupBy.fromJson(e))).toList();
  print(mySelectedEvents);
  return mySelectedEvents;
}

输出结果

  • 打印response得到接口返回的原始数据:
    [{date: 2022-09-17, eventDescp: azerty, eventTitle: azertyui}, {date: 2022-09-17, eventDescp: 11, eventTitle: AZE}, {date: 2022-09-17, eventDescp: 22, eventTitle: 4556}, {date: 2022-09-20, eventDescp: 77, eventTitle: HHJ}, {date: 2022-09-17, eventDescp: 44, eventTitle: BYYY}]
    
  • 打印mySelectedEvents得到的是Future对象列表:
    [Instance of 'Future<GroupBy>', Instance of 'Future<GroupBy>', Instance of 'Future<GroupBy>', Instance of 'Future<GroupBy>', Instance of 'Future<GroupBy>']
    

解决方案

问题根源

  1. response.map((e) async => GroupBy.fromJson(e))中使用了async,导致每个map元素都是Future<GroupBy>,转成列表后自然是Future对象的集合。
  2. 即便完成异步转换,得到的只是GroupBy对象的列表,还需要进一步按日期分组,转换成目标Map结构。

修改后的代码

情况1:GroupBy.fromJson是同步方法

如果GroupBy.fromJson内部没有异步操作,直接去掉async,再按日期分组:

loadPreviousEvents() async {
  var url = 'http://prospection.global-aeit.com/getEvents.php';
  var res = await http.get(Uri.parse(url));
  var response = json.decode(res.body) as List;
  
  // 将接口数据转成GroupBy对象列表
  var groupByItems = response.map((e) => GroupBy.fromJson(e)).toList();
  
  // 构建目标Map:日期为键,事件列表为值
  Map<String, List<Map<String, String>>> mySelectedEvents = {};
  for (var item in groupByItems) {
    String date = item.date; // 假设GroupBy类包含date、eventTitle、eventDescp属性
    Map<String, String> event = {
      'eventTitle': item.eventTitle,
      'eventDescp': item.eventDescp,
    };
    
    // 按日期分组添加事件
    if (!mySelectedEvents.containsKey(date)) {
      mySelectedEvents[date] = [];
    }
    mySelectedEvents[date]!.add(event);
  }
  
  print(mySelectedEvents);
  return mySelectedEvents;
}

情况2:GroupBy.fromJson是异步方法

如果GroupBy.fromJson内部有异步操作(比如读取本地文件),需要用Future.wait等待所有转换完成:

loadPreviousEvents() async {
  var url = 'http://prospection.global-aeit.com/getEvents.php';
  var res = await http.get(Uri.parse(url));
  var response = json.decode(res.body) as List;
  
  // 等待所有异步转换完成,得到GroupBy对象列表
  var groupByItems = await Future.wait(
    response.map((e) async => GroupBy.fromJson(e)).toList()
  );
  
  // 构建目标Map(逻辑同同步情况)
  Map<String, List<Map<String, String>>> mySelectedEvents = {};
  for (var item in groupByItems) {
    String date = item.date;
    Map<String, String> event = {
      'eventTitle': item.eventTitle,
      'eventDescp': item.eventDescp,
    };
    
    if (!mySelectedEvents.containsKey(date)) {
      mySelectedEvents[date] = [];
    }
    mySelectedEvents[date]!.add(event);
  }
  
  print(mySelectedEvents);
  return mySelectedEvents;
}

关键说明

  • 先确保完成所有数据转换,得到GroupBy对象的列表,而非Future列表。
  • 通过遍历分组,将每个事件按日期归类,最终生成和原代码一致的Map结构。

内容的提问来源于stack exchange,提问作者Zana Souleymane Coulibaly

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.15 00:25:32