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

Flutter/Dart无法存入HTTP请求结果到List:类型转换异常问题

解决:type 'String' is not a subtype of type 'int' of 'index' 异常

错误原因

接口返回的results是数组类型(对应Dart中的List),但你的代码直接用字符串"cardBillsTotal"作为索引访问results,相当于把List当成Map操作,必然触发类型不匹配异常。

看接口返回结构:

{"results":[{"firstName":"Θωμάς",..."cardBillsTotal":[{"serial":"884221337251",...}]},...]}

results是数组,数组内的每个元素才是包含cardBillsTotal字段的对象。


修复后的代码

1. 修正parseBills方法

如果需要合并所有results元素里的cardBillsTotal为一个列表:

List<Evsebill> parseBills(String responseBody) {
  final decoded = jsonDecode(responseBody);
  final List<Map<String, dynamic>> allBills = [];
  // 遍历results数组,取出每个元素的cardBillsTotal并合并
  for (final result in decoded["results"] as List) {
    final bills = result["cardBillsTotal"] as List;
    allBills.addAll(bills.cast<Map<String, dynamic>>());
  }
  return allBills.map<Evsebill>((json) => Evsebill.fromJson(json)).toList();
}

如果只需要取results数组第一个元素的cardBillsTotal:

List<Evsebill> parseBills(String responseBody) {
  final decoded = jsonDecode(responseBody);
  // 先取results数组的第一个元素,再访问cardBillsTotal
  final parsed = decoded["results"][0]["cardBillsTotal"].cast<Map<String, dynamic>>();
  return parsed.map<Evsebill>((json) => Evsebill.fromJson(json)).toList();
}

2. 修正fetch方法

同步调整setState内的逻辑,确保正确访问数组结构:

Future<List<Evsebill>> fetch() async {
  String? token = await this.storage.read(key: "token");
  Map<String, String> headers = {
    "Content-Type": "application/json",
    "Accept": "application/json",
    "Authorization": "Bearer " + (token ?? ""),
  };
  final response = await http.get(Uri.parse(
      this.serverIP + ':' + this.serverPort +
          '/user/contractedChargeTransactionsList?page=1&limit=10&year=eq:2022'),
      headers: headers);
  
  if (response.statusCode == 200) {
    final decoded = jsonDecode(response.body);
    setState(() {
      // 合并所有results的cardBillsTotal示例
      List<Map<String, dynamic>> rawBills = [];
      for (final result in decoded["results"] as List) {
        rawBills.addAll((result["cardBillsTotal"] as List).cast<Map<String, dynamic>>());
      }
      cardBills = rawBills;
      
      // 若只取第一个result的cardBillsTotal,替换为下面一行:
      // cardBills = decoded["results"][0]["cardBillsTotal"] as List;
      
      var result = cardBills.map((e) => Evsebill.fromJson(e)).toList();
    });
    return cardBills.map((e) => Evsebill.fromJson(e)).toList();
  } else {
    throw Exception('Failed to load Bills');
  }
}

额外优化建议

  • 访问数组前增加非空判断,避免下标越界:
    if ((decoded["results"] as List).isNotEmpty) {
      // 执行后续操作
    }
    
  • JSON字段类型转换容错:接口返回的数值可能是num类型(整数/浮点数),直接as double可能报错,建议修改为:
    value: (json['value'] as num).toDouble(),
    vat: (json['vat'] as num).toDouble(),
    total: (json['total'] as num).toDouble(),
    

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.16 16:45:35