1 type Map<K, V> @abstract = 2 let map = StdMap<K, V>.new 3 let mut is_invoking_callbacks = false 4 let on_added_callbacks = StdList<K * V -> Unit>.new 5 let on_removed_callbacks = StdList<K * V -> Unit>.new 6 let tokens = StdList<Token>.new 7 8 let invoke_callbacks (callbacks : StdList<K * V -> Unit> 9 k : K 10 v : V) = 11 assert not is_invoking_callbacks 12 is_invoking_callbacks = true 13 14 for f in callbacks do 15 f k v 16 17 is_invoking_callbacks = false 18 19 def is_empty = map.is_empty 20 def is_not_empty = map.is_not_empty 21 22 def try_get (k : K) = map.try_get k 23 def contains (k : K) = map.contains k 24 25 fun get (k : K) = map[k] 26 27 def subscribe (f : K * V -> Unit) (g : K * V -> Unit) = 28 assert not is_invoking_callbacks 29 on_added_callbacks.add f 30 on_removed_callbacks.add g 31 32 Token { assert not is_invoking_callbacks 33 on_added_callbacks.remove f 34 on_removed_callbacks.remove g } 35 36 def bind (f : K * V -> Unit) (g : K * V -> Unit) = 37 assert not is_invoking_callbacks 38 on_added_callbacks.add f 39 on_removed_callbacks.add g 40 41 for k, v in map do 42 f k v 43 44 Token { assert not is_invoking_callbacks 45 on_added_callbacks.remove f 46 on_removed_callbacks.remove g 47 48 for k, v in map do 49 g k v } 50 51 def subscribe (f : K * V -> Unit 52 g : K * V * V -> Unit 53 h : K * V -> Unit) = 54 let values = StdMap<K, V>.new 55 subscribe 56 { k v -> 57 if not values.contains k then 58 values.add k v 59 f k v 60 else 61 let prev_v = values[k] 62 values[k] = v 63 g k prev_v v } 64 { k v -> 65 if not contains k then 66 values.remove k 67 h k v } 68 69 def bind (f : K * V -> Unit 70 g : K * V * V -> Unit 71 h : K * V -> Unit) = 72 let token = subscribe f g h 73 for k, v in map do 74 f k v 75 76 Token { token.discard 77 for k, v in map do 78 h k v } 79 80 fun destruct = 81 for i = tokens.size - 1 downto 0 do 82 tokens[i].discard 83 84 type MutMap<K, V> @[mut_of Map] = 85 inherit Map<K, V> 86 87 def insert (k : K) (v : V) = 88 assert not is_invoking_callbacks 89 90 let result = map.insert k v 91 92 if result <> Some v then 93 if result ? Some prev_v then 94 invoke_callbacks on_removed_callbacks k prev_v 95 96 invoke_callbacks on_added_callbacks k v 97 98 result 99 100 fun set (k : K) (v : V) = 101 let result = insert k v 102 assert result.is_some 103 104 def add (k : K) (v : V) = 105 assert not is_invoking_callbacks 106 107 map.add k v 108 invoke_callbacks on_added_callbacks k v 109 110 def remove (k : K) = 111 assert not is_invoking_callbacks 112 113 let v = map[k] 114 map.remove k 115 invoke_callbacks on_removed_callbacks k v 116 117 def push_token (token : Token) = 118 tokens.add token 119 120 def as_readonly = self as Map<K, V> 121