Map built with Map.fromIterable instead of a for element

ID

dart.performance.prefer_for_elements_map_fromiterable

Severity

info

Remediation Complexity

medium

Remediation Risk

low

Remediation Effort

low

Resource

Idiom

Language

Dart

Description

Reports a Map.fromIterable call, which a map literal with a for element expresses directly. Map.fromIterables and Map.fromEntries are not reported - neither has a for-element equivalent that is as short.

Rationale

Map.fromIterable takes its key and value as closures, so building a map of n entries allocates two closures once and then calls them n times through a function pointer, none of which the compiler can see through. Its typing is worse than the cost: the constructor is declared over dynamic, so the key and value closures receive dynamic parameters and the inferred result is a Map of dynamic to dynamic unless every type argument is written out by hand - which is why the closures in real code so often contain a cast. A map literal with a for element has no closures, infers both type arguments from the expressions, and reads in the order the entries are produced.

The following code illustrates the pattern detected by this rule:

class Catalog {
  final List<int> ids;

  Catalog(this.ids);

  Map<int, String> labels() {
    // FLAGGED: Map built with Map.fromIterable instead of a for element
    return Map.fromIterable(
      ids,
      key: (id) => id as int,
      value: (id) => 'item-$id',
    );
  }
}

Remediation

Rewrite as a map literal with a for element - {for (final id in ids) id: 'item-$id'} - and drop the casts the dynamic parameters forced. Where entries come from an iterable of pairs, Map.fromEntries is the better constructor.

Configuration

This detector does not need any configuration.

© 2026 Xygeni. All rights reserved