【问题标题】:RangeError (index): Invalid value: Valid value range is empty: 1RangeError(索引):无效值:有效值范围为空:1
【发布时间】:2020-09-22 17:38:46
【问题描述】:

在尝试自己解决这个问题一整天后,我不得不来寻求帮助。

我正在尝试构建这个 ListView.builder,它有固定数量的 itemCount。它使用从本地存储的 JSON 文件中检索的数据构建小部件。

我正在使用 Provider 来传递这些数据。问题是,在应用程序启动或热重启时,ListView.builder 变为红色并显示错误,然后在四分之一秒后显示我的数据。

我明白为什么会发生这种情况,我从 json 获得的数据列表最初是空的。所以我把三元运算符像:provider.data == null ? CircularProgressIndicator() : ListView.builder... 但这并不能阻止它崩溃。

我不知道为什么,这让我发疯。这是完整的代码:

我们在这里谈论的是名为 RecommendedCardList 的小部件,它通过以随机数(在列表长度范围内)作为索引来显示上述列表中的小部件。

我在 HomeScreen 上有类似的 ListView,称为 CategoryCardList,它的工作方式与 RecommendedCardList 类似,但我没有遇到这个问题。主屏幕的其余部分也显示良好,只有RecommendedCardList 的部分会在短时间内变红。

主屏幕类:

    class HomeScreen extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    // Get user's screen properties
    // We are using this properties to adjust size accordingly
    // In order to achieve maximum responsivnes for different screen sizes
    var height = MediaQuery.of(context).size.height;
    var width = MediaQuery.of(context).size.width;

    var repoProvider = Provider.of<Repository>(context);
    var recipeDataList = repoProvider.recipeDataList;

    return Container(
      color: backgroundColor,
      child: repoProvider.recipeDataList == null
          ? Center(child: CircularProgressIndicator())
          : Padding(
              padding: contentPadding,
              child: ListView(
                children: <Widget>[
                  AppTitle(),
                  SizedBox(
                    height: height * 0.03,
                  ),
                  Column(
                    children: <Widget>[
                      CategoryAndSeeAll(),
                      CategoryCardsList(height: height, provider: repoProvider),
                    ],
                  ),
                  SizedBox(
                    height: height * 0.05,
                  ),
                  Container(
                    width: double.infinity,
                    height: height * 0.1,
                    decoration: BoxDecoration(
                      border: Border.all(color: accentColor),
                    ),
                    child: Text(
                      'Reserved for AD',
                      textAlign: TextAlign.center,
                    ),
                  ),
                  SizedBox(
                    height: height * 0.05,
                  ),
                RecommendedCardsList(height: height, width: width, recipeDataList: recipeDataList),
                ],
              ),
            ),
    );
     }



       }

RecommendedCardsList 类:

class RecommendedCardsList extends StatelessWidget {
  const RecommendedCardsList({
    Key key,
    @required this.height,
    @required this.width,
    @required this.recipeDataList,
  }) : super(key: key);

  final double height;
  final double width;
  final recipeDataList;
  @override
  Widget build(BuildContext context) {

    return Container(
            height: height * 0.30,
            child: ListView.builder(
                scrollDirection: Axis.horizontal,
                itemCount: numberOfRecommendedRecipes,
                itemBuilder: (context, counter) {
                  int randomNumber = Random().nextInt(recipeDataList.length);
                  return Row(
                    mainAxisAlignment: MainAxisAlignment.spaceBetween,
                    children: <Widget>[
                     RecommendedCard(
                        width: width,
                        height: height,
                        imagePath: recipeDataList.elementAt(randomNumber).image,
                        text: recipeDataList.elementAt(randomNumber).title,
                      ),
                    ],
                  );

                }),





          );
  }
}

存储库类:

class Repository extends ChangeNotifier {
  Repository() {
    loadJson();
  }

  var _recipeData;


  List<RecipeModel> _recipeDataList = [];
  List<RecipeModel> get recipeDataList => _recipeDataList;

  void loadJson() async {

    var json = await rootBundle.loadString('assets/recipes.json');
    var parsedJson = jsonDecode(json);
    for (var item in parsedJson) {
      _recipeData = RecipeModel.fromJson(item);
      _recipeDataList.add(_recipeData);
    }
    //print('Title:${_recipeDataList[0].title}\nImage:${_recipeDataList[0].image}'); // For debugging

    notifyListeners();
  }
}

【问题讨论】:

  • 这个变量(第二个块代码上的numberOfRecommendedRecipes)来自哪里?
  • 您是否通知更改并重建HomeScreen?你可以用FutureProvider
  • @RocignoMedeiros 这只是我的“values.dart”文件中的一个整数值。我敢存储一些简单的值。它基本上设置为 6。因为我只想要这些小部件中的 6 个。
  • @SanjaySharma 当然我正在调用 notifyListeners,如果我不这样做,什么都不会更新。就像我说的那样,我的东西出现了,但是那个特定的列表生成器暂时抛出错误:(混淆 af.
  • 实际错误是: RangeError (max): Must be positive and

标签: flutter dart


【解决方案1】:

此错误与代码在您的列表中搜索索引并且该索引超过您的列表长度有关。

我认为错误在于那部分:

int randomNumber = Random().nextInt(recipeDataList.length);

假设长度为 10,随机函数将检索 0 到 10 之间的 num,但最后一个索引是 9。

考虑到这一点,我有两个建议:

1)

// changing ternary logic
(repoProvider.recipeDataList == null && repoProvider.recipeDataList.length > 0)

2)

// inside ListView.Builder change to get the list length
itemCount: recipeDataList.length

【讨论】:

  • 1.不工作,同样的错误发生。我在 HomeScreen 和 RecommendedCardsList 中都试过了。。 2. 这个列表有 50 个项目长,我不需要那么多小部件,这就是为什么我在 itemCount 上设置不同的值......它不是 Random.NextInt 相关的,因为我试过没有它和它还是一样的:D
  • 实际上 1. 按原样工作。我不得不否定它只是因为我的小部件位置。干得好。
【解决方案2】:

将以下条件放在RecommendedCardsList 小部件的build() 中作为第一行。

if(recipeDataList == null || recipeDataList.length == 0){
  return Container();
}

【讨论】:

  • 没有区别,因为我设置了 recipeDataList = repoProvider.recipeDataList ...它在代码中:)
  • 能否确认numberOfRecommendedRecipes的值是否大于列表大小?
  • 我将它添加到第一篇文章中......我在该列表中有 40-50 项,它不是更多:)
  • 这修复了它!谢谢兄弟,给我喝酒
  • 您也可以在HomeScreen 中更改此条件以使用repoProvider.recipeDataList == null &amp;&amp; repoProvider.recipeDataList.length !=0 修复此repoProvider.recipeDataList == null
猜你喜欢
  • 1970-01-01
  • 2021-06-16
  • 2019-12-01
  • 2019-07-25
  • 2020-02-16
  • 2021-10-06
  • 2021-11-13
  • 2021-01-01
  • 2020-10-07
相关资源
最近更新 更多