Flutter-从List.map()获取迭代索引

时间:2019-03-04 20:03:39

标签: loops dictionary indexing dart flutter

我在网上搜索了很多答案。

我在字母列表上写了迭代,然后使用“地图”将卡片放在屏幕上

在代码中,您可以看到我做了一行,并使用卡上所有userBoard上打印的“地图”到屏幕。 我想在其中添加一些逻辑,因此我需要获取elemnt的ID(用于Taping事件)。 有办法可以做到吗?

实际上我想通过userBoard获取特定的元素索引

代码:

Widget build(BuildContext context) {
return Row(
  mainAxisAlignment: MainAxisAlignment.spaceEvenly,
  children: <Widget>[
        Row(
          children: userBoard
              .map((element) => Stack(children: <Widget>[
                    Align(
                      alignment: Alignment(0, -0.6),
                      child: GestureDetector(
                        onTap: (() {
                          setState(() {
                            // print("element=${element.toString()}");
                            // print("element=${userBoard[element]}");
                          });
                        }),
                        child: SizedBox(
                          width: 40,
                          height: 60,
                          child: Card(
                              shape: RoundedRectangleBorder(
                                borderRadius: BorderRadius.circular(5.0),
                              ),
                              child: Center(
                                child: Text(element,
                                    style: TextStyle(fontSize: 30)),
                              )),
                        ),
                      ),
                    )
                  ]))
              .toList(),
        )
      ],
    ),

}

Picture - each card is "element" of the map. I want to get the indexes for the function onTap.

谢谢。

17 个答案:

答案 0 :(得分:17)

如果要迭代的最简单方法

我们可以使用新功能扩展Iterable

import 'dart:core';

extension IndexedIterable<E> on Iterable<E> {
  Iterable<T> mapIndexed<T>(T Function(E e, int i) f) {
    var i = 0;
    return map((e) => f(e, i++));
  }
}

用法:

myList.mapIndexed((element, index) {});

取自here

答案 1 :(得分:6)

您可以简单地使用 mapIndexed 方法:

userBoard.mapIndexed(
  (int index, element) => Container( ... ))
     .toList();

这是 FIC 包的众多扩展之一:https://pub.dev/packages/fast_immutable_collections


如果您不想将包添加到您的项目中,您可以只复制扩展本身:

extension FicListExtension<T> on List<T> {

  /// Maps each element of the list.
  /// The [map] function gets both the original [item] and its [index].
  Iterable<E> mapIndexed<E>(E Function(int index, T item) map) sync* {
    for (var index = 0; index < length; index++) {
      yield map(index, this[index]);
    }
  }
}

注意:我是该软件包的作者之一。


更新:我现在已经删除了一些方法,例如 FIC package 中的 Iterable.mapIndexed(),因为 Google 在他们的 collection package 中添加了一个类似的方法,并且我希望两个包都兼容。

答案 2 :(得分:4)

Dart 发布了 collection 包,该包带有所有可迭代对象的 mapIndexed 扩展。

import 'package:collection/collection.dart';

void main() {
  final fruitList = ['apple', 'orange', 'mango'];
  final withIndices = fruitList.mapIndexed((index, fruit) => "$index - $fruit");
  print(withIndices);
}

(DartPad)

该软件包带有各种方便的扩展和有用的工具来处理集合。

答案 3 :(得分:2)

使用List.generate的另一种方法:

var list = ['y', 'e', 's'];
var widgets = List.generate(list.length, (i) => Text(list[i]));

答案 4 :(得分:2)

您可以尝试

children: [
          for(int index = 0; index < list.length; index++)
            Text(list[index])
        ]

答案 5 :(得分:1)

要访问索引,您需要使用asMap运算符将列表转换为地图。

示例

final fruitList = ['apple', 'orange', 'mango'];
final fruitMap = myList.asMap(); // {0: 'apple', 1: 'orange', 2: 'mango'}

// To access 'orange' use the index 1.
final myFruit = fruitMap[1] // 'orange'

// To convert back to list
fruit fruitListAgain = fruitMap.values.toList();

您的代码

userBoard.asMap().map((i, element) => MapEntry(i, Stack(
  GestureDetector(onTap: () {
    setState(() {
      // print("element=${element.toString()}");
      // print("element=${userBoard[i].toString()}");
    });
  }),
))).values.toList();

答案 6 :(得分:1)

您可以使用 asMap() 和 entris.map() 来获取索引。

list.asMap().entries.map((e) {
      var index = e.key;
      var value = e.value;
      // ...
    }

答案 7 :(得分:1)

也可以尝试以下方法:

list.asMap().keys.toList().map((index) {
  // var item = list[index];
  // index is the index of each element.
  return youFunction(index);
});

我也在这里的博客中写了其他方法。 https://medium.com/@channaly/map-with-index-in-dart-flutter-6e6665850ea8

答案 8 :(得分:0)

您可以先使用here

enumerate(userBoard).map((indexedValue) {
  final index = indexedValue.index;
  final element = indexedValue.value;
  // ...
})

答案 9 :(得分:0)

选择列表的当前元素时,您可以即时获取索引:

import 'package:enumerable/enumerable.dart';

void main() {
  final userBoard = ['Jack', 'Adam', 'Harry'];
  final list =
      userBoard.select$1((user, index) => Person(user, index)).toList();
  print(list);
}

class Person {
  String name;
  int index;
  Person(this.name, this.index);
  String toString() => '$name-$index';
}

结果:

[Jack-0, Adam-1, Harry-2]

答案 10 :(得分:0)

使用map将您的列表转换为另一个列表。

var yourList = ['A', 'B', 'C'];
var textList = yourList.map((e) => Text(e)).toList();

用法:

Column(
  children: textList,
)

答案 11 :(得分:0)

另一个解决方案是获取对象的hascode与int唯一 示例:

yourClass.hasCode()

这将为每次迭代返回一个ID,例如123456789

您在需要时在其他小部件中使用

onSelectChanged: (d) {
    setState(() {
       selectedRow = d == true ? object.hascode : null;
    });
 },
 selected: object.hascode == selectedRow,

答案 12 :(得分:0)

它在 dart 中非常简单直接。

myList.map((item) =>
print(myList.indexOf(item));//here I printing index             
).toList()

答案 13 :(得分:0)

没有内置函数来获取迭代索引。

您可能想要的是一个map,它可以为您提供索引:

children: enumerate(
  list,
  (index, item) => Text("event_$index")
).toList();

enumerate的实现很简单:

Iterable<E> enumerate<E, T>(
    Iterable<T> items, E Function(int index, T item) f) {
  var index = 0;
  return items.map((item) {
    final result = f(index, item);
    index = index + 1;
    return result;
  });
}

答案 14 :(得分:0)

当列表中没有重复的元素时,可以使用list.indexOf进行索引。

示例

userBoard.map((element) {
  // get index
  var index = userBoard.indexOf(element);
  return Container(

  );
}).toList()

答案 15 :(得分:0)

您可以使用list.asMap()

var result = list.asMap().map((e) => '${e[0]} - ${e[1]});
print(result);

https://api.dartlang.org/stable/2.2.0/dart-core/List/asMap.html

答案 16 :(得分:-5)

这不起作用!

List myList = ['a', 'b', 'c'];

myList.map( (val, index) {
    // This does not work!
    // Which index am I on?
})

解决方案

Container(
            width: MediaQuery.of(context).size.width,
            height: 170.0,
            child: ListView.builder(
              scrollDirection: Axis.horizontal,
              itemCount: myList.length,
              itemBuilder: (context, int index) {
                return ...//use index of item
              },
            ),
          )