Dart: Collections

Carlos Costa

Collections são objetos que representam grupos de objetos.

No Dart existem 3 tipos de collections mais comuns:

  • List: os objetos são identificado por índices
  • Set: usado para armazenar apenas objetos únicos
  • Map: os objetos são organizados no padrão chave e valor

List


Listas servem para agrupar outros objetos e seus item são identificados por índices

Listas sempre serão tipadas, seja de forma explícita ou implícita.

Exemplo de tipagem explícita:

List<String> ls = ['foo', 'bar', 'span'];

Exemplo de tipagem implícita:

var ls = [1, 2, 3] //Type: List<int>

No exemplo anterior, todos os items são do tipo int, logo, nossa lista será tipada como List<int>. Ao tentar adicionar um novo item de um tipo diferente teremos o seguinte erro.

ls.add('foo'); 👇

🚨 Error: The argument type ‘String’ can’t be assigned to the parameter type ‘int’.

Listas são iterables, isso significa que seus items podem ser acessados sequencialmente.

var ls = [1, 2, 3];
print(ls is Iterable) //true

Iterando sobre uma lista.

var ls = ['foo', 'bar', 'span'];

for (var element in ls) {
  print(element);
}// foo, bar, span

O objeto List oferece vários métodos para manipulação de uma lista. Métodos para iteração, adição de novos item, remoção de item, busca de items, etc…

Exemplo: Somando todos os items de uma lista com o método .reduce().

var ls = [1, 2, 3, 4, 5];
ls.reduce((total, element) => total + element); // 15;

Exemplo: Filtrando todos os elementos maiores que 3 com o método .where().

var ls = [1, 2, 3, 4, 5];
ls.where((element) => element > 3); //[4, 5]

Exemplo: Concatenando todos os items com o método .join().

var ls = ['foo', 'bar', 'span'];
ls.join('-'); // foo-bar-span

Referência completa do objeto List: https://api.dart.dev/stable/2.18.4/dart-core/List-class.html

Set


Set é uma coleção que aceita apenas elementos únicos

Item duplicados dentro de um set são excluídos.

Exemplo:

var st = {'foo', 'bar', 'span', 'foo'};
print(st); // foo, bar, span

As regras de tipagem explícita e implícita das listas também se aplicam aos sets.

var st = {'foo', 'bar', 'span', 'foo'};
print(st); // foo, bar, span

st.add(1);

🚨 Error: The argument type ‘int’ can’t be assigned to the parameter type ‘String’

Um List pode ser convertido em um Set de forma bem simples e vice versa, essa funcionalidade é bem útil para remover itens duplicados de um List.

Nesse exemplo usaremos os métodos .toSet() e toList().

List<int> ls = [3, 1, 1, 4, 2, 2, 3, 1, 4, 5].toSet().toList();
print(ls); //[3, 1, 4, 2, 5]

Referência completa do objeto Set: https://api.dart.dev/stable/2.18.4/dart-core/Set-class.html

Map


Map é uma coleção que identifica seus items por chave e valor

Exemplo:

var mp = {
  'name': 'Peter',
  'lastName': 'Parker',
  'job': 'hero',
  'City': 'Manhatan'
}; //Map<String, String>

Maps são generatics(Map<k, v>) isso significa que podemos atribuir tipos específicos pas as chaves e valores.

Map<int, Function> mp = {
  1: () => 'first',
  2: () => 'second',
  3: () => 'third',
  4: () => 'fourth'
};

Existem várias formas de iterar sobre um Map.

Map<String, String> mp = {
  'name': 'Peter',
  'lastName': 'Parker',
  'job': 'hero',
  'City': 'Manhatan'
}; //Map<String, String>

Usando o método .forEach:

mp.forEach((key, value) {
  print("$key -> $value");
});

Usando a propiedade .entries:

for (var element in mp.entries) {
  print('${element.key} -> ${element.value}');
}

Iterando somente sobre as chaves usando o .keys:

mp.keys.forEach((keys) {
  print(keys);
}); // name, lastName, job, city

Iterando somente sobre os values usando o .values:

mp.values.forEach((value) {
  print(value);
}); // Peter, Parker, hero, Manhatan

Referência completa do objeto Map: https://api.dart.dev/stable/2.18.4/dart-core/Map-class.html

Operador spread


  • spread operator (…): usado para adicionar os items de uma collection em outra collection.
  • null-aware spread operator (…?): adiciona item de uma collection em outra collection, mas verifica se a collection é nula antes de adicionar os items.

Exemplos:

List<int> l1 = [1, 2, 3];
List<int> l2 = [4, 5, 6];
List<int> l3 = [...l1, ...l2]; // [1, 2, 3, 4, 5, 6]
var l1 = [1, 2, 3];
var l2 = null;

//verifica se l2 é nulo antes de adicionar os items
var l3 = [...l1, ...?l2]; // [1, 2, 3]

Operadores de controler


Também é possível usar operadores de controle(if and for) para manipular collections.

Exemplo: adicionar um item a uma lista se uma condição for verdadeira.

var a = 10;
var l1 = [1, 2, 3, if (a > 3) a]; // [1, 2, 3, 10]

Exemplo: comport listas utilizando o for.

var l1 = [3, 4, 5];
var l2 = [1, 2, 3, for (var i in l1) i]; // [1, 2, 3, 3, 4, 5]

Referências