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

Flutter空安全迁移时默认List构造函数不可用报错解决

报错原因

空安全模式下Dart禁用了List(int length)默认构造函数,才会抛出这个错误:

  • 空安全上线前,这个构造器会生成指定长度、所有元素初始值为null的定长列表,是旧版本里很常见的写法。
  • 启用空安全后,非空类型的集合不允许出现null元素,这个会默认生成全null值的构造器直接被从核心API中移除,官方要求替换为列表字面量、List.filled、List.generate这三类不会产生非法null值的列表构造方式。

你代码里的三处List(n)写法,本质只是为了获得n次迭代的执行次数,根本没有使用列表内存储的元素,属于旧版本中“借列表实现循环”的特殊写法,在空安全下需要替换为合法实现。

修改方案

有两种常见改法,第一种是最小改动保留原有链式逻辑,第二种是更高效的规范写法,推荐第二种。

最小改动方案

只需要把所有List(n)替换为List.filled(n, 0)即可,List.filled会生成一个所有元素都为你指定的默认值的定长列表,完全符合空安全要求,其余代码逻辑不需要调整:

List<CardModel> createCards() {
  List<String> asset = [];
  List.filled(10, 0).forEach((f) => asset.add('0${(asset.length + 1)}.png'));
  List.filled(10, 0).forEach((f) => asset.add('0${(asset.length - 10 + 1)}.png'));
  return List.filled(20, 0).map((f) {
    int index = Random().nextInt(1000) % asset.length;
    String _image =
        'assets/' + asset[index].substring(asset[index].length - 6);
    asset.removeAt(index);
    return CardModel(
        id: 20 - asset.length - 1, image: _image, key: UniqueKey());
  }).toList();
}

这种写法的缺点是会生成三个用完即弃的临时列表,存在不必要的内存开销。

推荐的规范写法

去掉冗余的临时列表,直接用for循环实现固定次数的迭代,最后用List.generate直接生成目标列表,既符合空安全规范,性能也更好,业务逻辑和原代码完全一致:

List<CardModel> createCards() {
  List<String> asset = [];
  // 替换原临时列表实现的循环
  for (int i = 0; i < 10; i++) {
    asset.add('0${asset.length + 1}.png');
  }
  for (int i = 0; i < 10; i++) {
    asset.add('0${asset.length - 10 + 1}.png');
  }
  // 直接生成目标列表,省去map、toList的中间步骤
  return List.generate(20, (_) {
    int index = Random().nextInt(1000) % asset.length;
    String _image = 'assets/' + asset[index].substring(asset[index].length - 6);
    asset.removeAt(index);
    return CardModel(
      id: 20 - asset.length - 1,
      image: _image,
      key: UniqueKey()
    );
  });
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.30 21:06:22