baml.Map
An insertion-ordered collection of key-value pairs.
Signature
class baml.Map<K extends baml.Hash & baml.ops.Equals, V>An insertion-ordered collection of key-value pairs.
Map<K, V> is spelled map<K, V> in type position. Keys must implement
baml.Hash and baml.ops.Equals. Equal keys must hash equally,
and their hash and equality must stay stable while stored in the map.
JSON and SDK boundaries still require string-keyed maps.
Iteration order is the order in which keys were first inserted: keys()
and values() follow it, set on an existing key keeps that key's original
position, and delete preserves the order of the entries that remain. This
is how JavaScript's
Map
and Python's dict behave — not the arbitrary order of a hash map.
Like arrays, maps are heap objects with reference semantics: a map passed to
a function or stored in another container is shared, and every mutating
method (set, delete, clear, …) is visible through every reference.
m[key] reads and m[key] = v writes through the map. Reading a key that
is not present raises baml.panics.MapKeyNotFound; writing one inserts it
at the end. get is the non-panicking read.
When V is nullable, a null returned by get, set or delete is
ambiguous between "no such key" and "the key's value is null". has is
the way to tell the two apart.
Source:<builtin>/baml/containers.bamlbytes 28396–32977
Instance methods
clear
(self) -> null throws neverRemoves every entry, leaving length() == 0.
The map object is emptied, not replaced, so every other reference to it
observes the empty map too. Rebind to a fresh {} to leave the original
alone.
delete
(self, key: K) -> V | null throws neverRemoves the entry for key and returns its value, or null if the key
was absent.
The entries that remain keep their insertion order, which costs O(n):
everything after the removed entry shifts down. An order-scrambling
O(1) removal is deliberately not offered — iteration order is part of
this type's contract.
Examples
let m: map<string, int> = {"a": 1, "b": 2};
m.delete("a") // 1
m.delete("a") // null (already gone)
get
(self, key: K) -> V | null throws neverReturns the value for key, or null if the key is absent. O(1).
The non-panicking counterpart of self[key], which raises
baml.panics.MapKeyNotFound where get returns null.
Examples
let m: map<string, int> = {"a": 1};
m.get("a") // 1
m.get("b") // null
get_or_insert
(self, key: K, default: V) -> V throws neverReturns the value for key, inserting default first if the key was
absent. Python's
dict.setdefault.
The map is touched only on insertion, and the new key is appended at the end of the iteration order.
default is an ordinary argument, so it is evaluated at the call site
whether or not it ends up being inserted. Guard an expensive or
side-effecting default behind has yourself.
Examples
let m: map<string, int> = {};
m.get_or_insert("k", 10) // 10 (inserted)
m.get_or_insert("k", 99) // 10 (existing — `99` ignored)
has
(self, key: K) -> bool throws neverReturns true if the map contains an entry for key. O(1).
Prefer this to get(key) != null: a key mapped to null is present,
but get cannot say so.
index
(self, key: K) -> V throws neverReads key, raising baml.panics.MapKeyNotFound if it is absent.
keys
(self) -> K[] throws neverReturns the keys, in insertion order.
The array is a snapshot, not a live view: later set and delete calls
do not change it, and mutating it does not change the map. Iterating it
while mutating the map is therefore safe.
length
(self) -> int throws neverReturns the number of entries. O(1).
set
(self, key: K, value: V) -> V | null throws neverInserts or replaces the entry for key and returns the previous value,
or null if key was absent. O(1).
Replacing an existing key keeps its original position in iteration
order; a new key is appended at the end. self[key] = value is the same
operation, minus the previous value.
Examples
let m: map<string, int> = {};
m.set("a", 1) // null (was absent)
m.set("a", 2) // 1 (returns the old value)
values
(self) -> V[] throws neverReturns the values, in the same order as keys() — so keys()[i] maps
to values()[i].
The array is a snapshot, but the values are not copied: a reference type is shared with the map, so mutating a value obtained here also mutates the one the map holds.
Implementations
baml.Concrete for T
Source:<builtin>/baml/core.bamlbytes 763–795
baml.ops.Equals for map<string, V>
Instance methods
eq
(self, other: map<string, V>) -> bool throws neverneq
(self, other: Self) -> bool throws neverWhether self and other differ. Defaults to !self.eq(other).
Override this only to compute the answer more directly; an override that
disagrees with !eq leaves the pair inconsistent. Equals for null
overrides it with a constant false, which is consistent because null
has exactly one value.
Source:<builtin>/baml/ns_ops/comparison.bamlbytes 13826–13976
baml.ops.Index for map<K, V>
Output = VInstance methods
index
(self, idx: K) -> V throws neverSource:<builtin>/baml/ns_ops/index.bamlbytes 2439–2606