How do I convert a Trie.Trie to an Array in Motoko?

I’m attempting to convert a Trie.Trie into an array. Go someone give me an example of how this is done. Thanks in advance!

1 Like

You could create an iterator using Trie.iter() and use Iter.toArray(), eg:

import Trie “mo:base/Trie”;
import Text “mo:base/Text”;
import Iter “mo:base/Iter”;

type Trie<K, V> = Trie.Trie<K, V>;
type Key = Trie.Key;

func key(t: Text) : Key { { key = t; hash = Text.hash(t) } };

let t0 : Trie<Text, Nat> = Trie.empty();
let t1 : Trie<Text, Nat> = Trie.put(t0, key(“one”), Text.equal, 1).0;
let t2 : Trie<Text, Nat> = Trie.put(t1, key(“two”), Text.equal, 2).0;

let my_array : [(Text, Nat)] = Iter.toArray(Trie.iter(t2));

This will give you an array of key/value pairs like so: [(“one”, 1), (“two”, 2)]

Or you could use Trie.toArray(), which takes a function that maps from key/value pairs to a third type (which could still be a key/value pair or for example just the value), see here:
https://github.com/dfinity/motoko-base/blob/890b56688ed47c45ca3baf68bfa5c5ea22b7de88/src/Trie.mo#L962

1 Like

Is there an example implementation of using the toArray function of the Trie? I am looking at the toArray source from the link, and the application is not jumping out at me…

Also, I am curious which is a more optimized implementation, using toArray on the Trie or using the iterator?

let myTrie
  : Trie.Trie<Text, Nat>
  = Trie.empty();

let myArray
  : [(Text, Nat)]
  = Trie.toArray<Text, Nat, (Text, Nat)>(myTrie, func (k, v) {
    (k, v);
  });

Trie.toArray seems optimal to me.

2 Likes

great! thank you…got this working :star_struck:

for posterity this is what I ended up doing:

public shared func getRecords() : async [Record] {
  let result : [Record] = 
    Trie.toArray<Text, Record, Record>(records, func(k, v)) {
      (v);
    });
  return results;
}