Introduction
I have been playing around with Flutter for a few months now and I'm starting to get a good grip on the concepts of dart, the language that drives flutter. I do, however, often find myself on google looking up array methods. I thought I'd cover them in this post for my own reference and also for anyone who faces the same predicament. Coming from a web/js background, the methods are very similar to Javascript array methods. Let's dive in.
Prerequisites
There really isn't any but let's mention something anyway.
- Flutter / Dart
- OOP Knowledge
You can follow along using DartPad, a playground for dart. You can also refer to the official docs.
Getting started
Open up DartPad and we'll get started.
Paste the following code inside dartpad and run it.
void main() {
List<String> fruits = ['mangoes','bananas','pears','oranges'];
print(fruits);
}
You will immediately notice the type annotation when declaring our fruits
variable. This improves readability and IntelliSense when using a code editor like Visual Studio Code. It is also type-safe, which means you cannot assign anything other than strings. The above code can also be written as
void main() {
var fruits = ['mangoes','bananas','pears','oranges'];
print(fruits);
}
What if we wanted to add items of different types? Well, the code immediately above will work. But you can also change List<String>
to List<dynamic>
. Now you can add integers, strings, booleans even other lists.
const and final
Can you guess what happens when we mark our list as either final
or const
? Let's find out.
Change your code to this
void main() {
final List<String> fruits = ['mangoes','bananas','pears','oranges'];
fruits.add('apples');
print(fruits);
}
Run it. You'll notice that apples have been added to our list. Marking as final means we cannot reassign our variable. We can, however, mutate our list. Now let's try something else.
void main() {
final List<String> fruits = ['mangoes','bananas','pears','oranges'];
fruits = [...fruits,'apples'];
print(fruits);
}
You will immediately get an error.
How can we mark our list as immutable? Yes, you already guessed it. Using the const
keyword. We can do this in two ways.
void main() {
final List<String> fruits = const ['mangoes','bananas','pears','oranges'];
//fruits.add('apples');
print(fruits);
}
void main() {
const List<String> fruits = ['mangoes','bananas','pears','oranges'];
//fruits.add('apples');
print(fruits);
}
Uncomment fruits.add('apples');
and try running both. The two implementations are not entirely similar. I will cover deeply when I also have a better understanding.
There's just one more thing to cover before we get down to the main event.
Creating lists
We've already seen one way of creating lists. That is what we have been using from the start of this article. We will cover a few more methods which might come in handy.
1.List(int length)
void main() {
var list = List(5);
print(list); //output - [null, null, null, null, null]
}
This creates a list of length 5 with null
as its items/values.
2.List.filled(int length,dynamic fill,{bool growable})
void main() {
var list = List.filled(5, "hello");
print(list); // output - [hello, hello, hello, hello, hello]
}
It takes in a length and whatever you want the list to fill at each index. You can also specify growable
, which accepts a boolean, as an optional named parameter.
void main() {
var list = List.filled(5, "hello",growable:true);
list.add('hello');
print(list); // output - [hello, hello, hello, hello, hello, hello]
}
growable
determines if we can add/remove items.
3.List.generate(int length, dynamic generator(int index),{bool growable})
void main() {
var list = List.generate(5,(index) =>index +2,growable:true);
print(list); //output - [2, 3, 4, 5, 6]
}
I believe you have already figured out what's going on with the generator. It takes in the index and returns whatever you want to fill at that index.
4.List.from(Iterable list,{bool growable})
void main() {
var list = List.generate(5,(index) =>"hello $index",growable:true);
print(list); //output - [hello 0, hello 1, hello 2, hello 3, hello 4]
var list2 = List.from(list,growable:false);
print(list2); //output - [hello 0, hello 1, hello 2, hello 3, hello 4]
}
This one creates a new list from another list or iterable.
There are a few more ways but these are the most common.
Now we can get started with the methods.
List methods and properties
1.add
We have already seen this method several times already. It is used to add items to a growable list.
void main() {
var fruits = ['mangoes','bananas'];
fruits.add('apples');
print(fruits); //output - [mangoes, bananas, apples]
}
2.remove
This method removes an object/item from a growable list. Make sure your values are unique else it removes only the first match.
void main() {
var fruits = ['mangoes','bananas','apples'];
fruits.remove('mangoes');
print(fruits); //output - [bananas, apples]
}
3.removeAt
This method removes the item at the specified index
void main() {
var fruits = ['mangoes','bananas','apples'];
fruits.removeAt(1);
print(fruits); //output - [mangoes, apples]
}
4.addAll
Adds all items of the specified Iterable.
void main() {
var fruits = ['mangoes','bananas','apples'];
var morefruits = ['peaches','plums'];
fruits.addAll(morefruits);
print(fruits); //output - [mangoes, bananas, apples, peaches, plums]
}
5.asMap
Returns a map representation of the List with the indices as keys and items of the array as the values.
void main() {
var fruits = ['mangoes','bananas','apples'];
print(fruits.asMap()); //output - {0: mangoes, 1: bananas, 2: apples}
}
6.insert
and insertAll
These are similar to add
and addAll
but you can specify the index where you would like to add the item(s).
void main() {
var fruits = ['mangoes','bananas','apples'];
var morefruits = ['peaches','plums'];
fruits.insertAll(1,morefruits);
print(fruits); //output - [mangoes, peaches, plums, bananas, apples]
}
7.getRange
Returns an Iterable of items in the range specified. You can then call toList
to convert the Iterable into a list.
void main() {
var fruits = ['mangoes','bananas','apples','peaches','plums'];
print(fruits.getRange(1,3).toList()); //output - [bananas, apples]
}
8.fillRange
Replaces all items in the range specified.
void main() {
var fruits = ['mangoes','bananas','apples','peaches','plums'];
fruits.fillRange(1,4,'pears');
print(fruits); //output - [mangoes, pears, pears, pears, plums]
}
9.lastIndexOf
and lastIndexWhere
lastIndexOf
allows you to get the index of the last item that you pass. This means that if you have more than one similar item/object it will get the index of the last one in the list.
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums'];
print(fruits.lastIndexOf('mangoes')); //output - 2
}
lastIndexWhere
is similar to lastIndexOf
except that it allows you to specify a test instead of an object/item. It then takes the index of the last item that passes the test
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums'];
print(fruits.lastIndexWhere((item)=> item == 'mangoes')); //output - 2
}
10.shuffle
Shuffles the items in the list randomly
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums'];
fruits.shuffle();
print(fruits); //output - [bananas, plums, peaches, mangoes, mangoes]
}
11.sort
Sorts the items of the list based on the passed argument which is normally a Comparable
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums','apples'];
fruits.sort((a,b)=> a.compareTo(b));
print(fruits); //output - [apples, bananas, mangoes, mangoes, peaches, plums]
}
void main() {
var numbers= [30,10,22,45,24,88,1,37,100,0];
fruits.sort((a,b)=> a - b);
print(numbers); //output - [0, 1, 10, 22, 24, 30, 37, 45, 88, 100]
}
```
12.`any`
Checks the items in the list and returns either true or false depending on whether any item in the list passes the test or not.
```
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums','apples'];
print(fruits.any((fruit)=>fruit.startsWith('a'))); //output - true
}
```
13.`every`
This is similar to `any` except that all items must pass the test instead of just one item.
```
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums','apples'];
print(fruits.every((fruit)=>fruit is String)); //output - true
}
```
14.`expand`
Expands every item in the list/iterable to zero or more items. One good use of this method is to duplicate items in the list.
```
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums','apples'];
print(fruits.expand((fruit)=> [fruit,fruit]).toList()); //output - [mangoes, mangoes, bananas, bananas, mangoes, mangoes, peaches, peaches, plums, plums, apples, apples]
}
```
15.`reduce` and `fold`
These combine the items of the list using the provided function and returns their combined value.
```
void main() {
var numbers = [10,20,30,40,50,60,70,80];
print(numbers.reduce((a,b)=>a+b)); //output - 360
}
```
`fold` takes in an initial value which is added to the combined value.
```
void main() {
var numbers = [10,20,30,40,50,60,70,80];
print(numbers.fold(100,(a,b)=> b+a)); //output - 460
}
```
16.`join`
Converts each item into a string, joins the passed string to all items and concatenates all items into one string.
```
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums','apples'];
print(fruits.join(' are fruits,')); //output - mangoes are fruits,bananas are fruits,mangoes are fruits,peaches are fruits,plums are fruits,apples
}
```
17.`map`
Returns a new Iterable with every item modified to fit the passed function. You can then call `toList` to convert to a list.
```
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums','apples'];
print(fruits.map((fruit)=> "$fruit are fruits").toList()); //output - [mangoes are fruits, bananas are fruits, mangoes are fruits, peaches are fruits, plums are fruits, apples are fruits]
}
```
18.`forEach`
Takes each item and applies the given function in their index order.
```
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums','apples'];
fruits.forEach((fruit){
print(fruit);
});
}
```
19.`followedBy`
Adds the passed list/iterable to your list.
```
void main() {
var fruits = ['mangoes','bananas','mangoes','peaches','plums','apples'];
print(fruits.followedBy(["coconuts","guavas"]).toList()); //output - [mangoes, bananas, mangoes, peaches, plums, apples, coconuts, guavas]
}
```
20.`take`
Takes in an integer and returns a list with only the first elements up to the length specified.
```
void main() {
var fruits = ['mangoes','bananas','peaches','plums','apples'];
print(fruits.take(3).toList()); //output - [mangoes, bananas, peaches]
}
```
## Summary
There are a few more methods that I did not outline here. They are also important and I would suggest you take a look at the [official docs](https://api.dartlang.org/stable/2.4.0/dart-core/List-class.html) to better understand these methods and more. The methods outlined here are those that I often find myself looking up.