Home > front end >  How to add value to existing key in a map data type?
How to add value to existing key in a map data type?

Time:08-07

I have a map data type, Map<String, List>, (todoData) and I want to add more strings to the list value.

final Map<String, List<String>> todoDate = {};

for example: {'Today': ['Code', 'Eat',]};
I want to add a 3rd String to the value, how do I do that?

CodePudding user response:

For adding to a list, use:

List<int> list = [1, 2, 3];
list.add(4);

For removing from a list:

list2.remove(2); // Remove the value "2"
list2.removeAt(0); // Remove the value at index 0

So, for your case, you can do:

todoDate["Today"]?.add("myNewValue"); // Add new value if 'Today' key exists.

For removing:

todoDate["Today"]?.remove("myNewValue"); // Remove the value "myNewValue"
todoDate["Today"]?.removeAt(2); // Remove the value at index 2

CodePudding user response:

In general, I would recommend not using Map as a way to structure data since it gives you all kinds of unsafe behavior we need to deal with. e.g. Dart is not able to tell us right away if the map contains the key "Today" already.

If it does not contain the key, we need to define a new list with our new entry instead of just adding to an existing one.

We can use the update function on Map to handle both cases like this:

void main() {
  final Map<String, List<String>> todoDate = {
    'Today': ['Code', 'Eat']
  };

  todoDate.update('Today', (list) => list..add('Learn Dart'),
      ifAbsent: () => ['Learn Dart']);

  print(todoDate); // {Today: [Code, Eat, Learn Dart]}
}

Personally, I don't really like this since we need a lot of code. We can, however, reduce the amount of code by adding an extension method to Map which contains List as values (name of extension and method should be renamed to something better):

void main() {
  final Map<String, List<String>> todoDate = {
    'Today': ['Code', 'Eat']
  };

  todoDate.appendToList('Today', 'Learn Dart');
  todoDate.appendToList('Yesterday', 'Learn Dart');

  print(todoDate); // {Today: [Code, Eat, Learn Dart], Yesterday: [Learn Dart]}
}

extension AppendToListOnMapWithListsExtension<K, V> on Map<K, List<V>> {
  void appendToList(K key, V value) =>
      update(key, (list) => list..add(value), ifAbsent: () => [value]);
}

But if we already know right away what keys we have in the Map (so keys are not dynamically created), we could instead just define a class. What this class should look like depends a lot of the application. But a simple example would be:

class Todo {
  final List<String> _tasks = [];

  void addTask(String task) => _tasks.add(task);
  void removeTask(String task) => _tasks.remove(task);

  @override
  String toString() => 'Todo: $_tasks';
}

void main() {
  final todayTasks = Todo()
    ..addTask('Code')
    ..addTask('Eat');

  todayTasks.addTask('Learn Dart');
  todayTasks.removeTask('Code');

  print(todayTasks); // Todo: [Eat, Learn Dart]
}

Maybe have some other class that contains the todayTasks variable. But the question does not really give enough context to come up with a detailed class design. :)

  •  Tags:  
  • dart
  • Related