about summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorKartik K. Agaram <vc@akkartik.com>2015-11-06 13:22:16 -0800
committerKartik K. Agaram <vc@akkartik.com>2015-11-06 13:22:30 -0800
commitf3760b0f2828250b4b5fb1a52601fe6b11ff328f (patch)
tree69ec57c652ff823e92146281ba656e3eaba57eb7
parent12f304a333ecee6326a8111e0d8e1c494ee92087 (diff)
downloadmu-f3760b0f2828250b4b5fb1a52601fe6b11ff328f.tar.gz
2379 - further improvements to map operations
Commands run:

  $ sed -i 's/\([^. (]*\)\.find(\([^)]*\)) != [^.]*\.end()/contains_key(\1, \2)/g' 0[^0]*cc
  $ sed -i 's/\([^. (]*\)\.find(\([^)]*\)) == [^.]*\.end()/!contains_key(\1, \2)/g' 0[^0]*cc
-rw-r--r--001help.cc11
-rw-r--r--010vm.cc4
-rw-r--r--011load.cc2
-rw-r--r--013update_operation.cc2
-rw-r--r--030container.cc8
-rw-r--r--034call.cc2
-rw-r--r--041jump_target.cc4
-rw-r--r--042name.cc2
-rw-r--r--046closure_name.cc8
-rw-r--r--048check_type_by_name.cc6
-rw-r--r--050scenario.cc4
-rw-r--r--052tangle.cc12
-rw-r--r--054dilated_reagent.cc2
-rw-r--r--057static_dispatch.cc4
-rw-r--r--058generic_container.cc2
-rw-r--r--059generic_recipe.cc10
-rw-r--r--075scenario_console.cc2
-rw-r--r--080trace_browser.cc20
-rw-r--r--081run_interactive.cc2
19 files changed, 56 insertions, 51 deletions
diff --git a/001help.cc b/001help.cc
index 3ed85e12..e42dc6a7 100644
--- a/001help.cc
+++ b/001help.cc
@@ -96,13 +96,18 @@ template<typename T> typename T::mapped_type& get(T& map, typename T::key_type c
   assert(iter != map.end());
   return iter->second;
 }
-template<typename T> typename T::mapped_type& get_or_insert(T& map, typename T::key_type const& key) {
-  return map[key];
-}
 template<typename T> typename T::mapped_type const& put(T& map, typename T::key_type const& key, typename T::mapped_type const& value) {
   map[key] = value;
   return map[key];
 }
+template<typename T> bool contains_key(T& map, typename T::key_type const& key) {
+  return map.find(key) != map.end();
+}
+template<typename T> typename T::mapped_type& get_or_insert(T& map, typename T::key_type const& key) {
+  return map[key];
+}
+//: The contract: any container that relies on get_or_insert should never call
+//: contains_key.
 
 :(before "End Includes")
 #include<assert.h>
diff --git a/010vm.cc b/010vm.cc
index 5f583a73..31749999 100644
--- a/010vm.cc
+++ b/010vm.cc
@@ -273,7 +273,7 @@ type_tree* new_type_tree(const string_tree* properties) {
   type_tree* result = new type_tree(0);
   if (!properties->value.empty()) {
     const string& type_name = properties->value;
-    if (Type_ordinal.find(type_name) == Type_ordinal.end()
+    if (!contains_key(Type_ordinal, type_name)
         // types can contain integers, like for array sizes
         && !is_integer(type_name)) {
       put(Type_ordinal, type_name, Next_type_ordinal++);
@@ -413,7 +413,7 @@ void dump_types_tree(const type_tree* type, ostream& out) {
 }
 
 void dump_type_name(recipe_ordinal type, ostream& out) {
-  if (Type.find(type) != Type.end())
+  if (contains_key(Type, type))
     out << get(Type, type).name;
   else
     out << "?";
diff --git a/011load.cc b/011load.cc
index 2c5806e8..51d2e8e7 100644
--- a/011load.cc
+++ b/011load.cc
@@ -47,7 +47,7 @@ long long int slurp_recipe(istream& in) {
   if (result.name.empty())
     raise_error << "empty result.name\n" << end();
   trace(9991, "parse") << "--- defining " << result.name << end();
-  if (Recipe_ordinal.find(result.name) == Recipe_ordinal.end()) {
+  if (!contains_key(Recipe_ordinal, result.name)) {
     put(Recipe_ordinal, result.name, Next_recipe_ordinal++);
   }
   if (Recipe.find(get(Recipe_ordinal, result.name)) != Recipe.end()) {
diff --git a/013update_operation.cc b/013update_operation.cc
index 13c7a3ad..a8feb065 100644
--- a/013update_operation.cc
+++ b/013update_operation.cc
@@ -10,7 +10,7 @@ void update_instruction_operations(recipe_ordinal r) {
   for (long long int index = 0; index < SIZE(get(Recipe, r).steps); ++index) {
     instruction& inst = get(Recipe, r).steps.at(index);
     if (inst.is_label) continue;
-    if (Recipe_ordinal.find(inst.name) == Recipe_ordinal.end()) {
+    if (!contains_key(Recipe_ordinal, inst.name)) {
       raise_error << maybe(get(Recipe, r).name) << "instruction " << inst.name << " has no recipe\n" << end();
       return;
     }
diff --git a/030container.cc b/030container.cc
index 2ad0a124..4ad2ee36 100644
--- a/030container.cc
+++ b/030container.cc
@@ -189,7 +189,7 @@ case GET: {
 :(code)
 const reagent element_type(const reagent& canonized_base, long long int offset_value) {
   assert(offset_value >= 0);
-  assert(Type.find(canonized_base.type->value) != Type.end());
+  assert(contains_key(Type, canonized_base.type->value));
   assert(!get(Type, canonized_base.type->value).name.empty());
   const type_info& info = get(Type, canonized_base.type->value);
   assert(info.kind == CONTAINER);
@@ -390,7 +390,7 @@ void insert_container(const string& command, kind_of_type kind, istream& in) {
   string name = next_word(in);
   // End container Name Refinements
   trace(9991, "parse") << "--- defining " << command << ' ' << name << end();
-  if (Type_ordinal.find(name) == Type_ordinal.end()
+  if (!contains_key(Type_ordinal, name)
       || get(Type_ordinal, name) == 0) {
     put(Type_ordinal, name, Next_type_ordinal++);
   }
@@ -412,7 +412,7 @@ void insert_container(const string& command, kind_of_type kind, istream& in) {
     for (type_tree** curr_type = &new_type; !inner.eof(); curr_type = &(*curr_type)->right) {
       string type_name = slurp_until(inner, ':');
       // End insert_container Special Uses(type_name)
-      if (Type_ordinal.find(type_name) == Type_ordinal.end()
+      if (!contains_key(Type_ordinal, type_name)
           // types can contain integers, like for array sizes
           && !is_integer(type_name)) {
         put(Type_ordinal, type_name, Next_type_ordinal++);
@@ -530,7 +530,7 @@ void check_invalid_types(const recipe_ordinal r) {
 void check_invalid_types(const type_tree* type, const string& block, const string& name) {
   if (!type) return;  // will throw a more precise error elsewhere
   // End Container Type Checks
-  if (type->value && (Type.find(type->value) == Type.end() || get(Type, type->value).name.empty())) {
+  if (type->value && (!contains_key(Type, type->value) || get(Type, type->value).name.empty())) {
     raise_error << block << "unknown type in " << name << '\n' << end();
   }
   if (type->left) check_invalid_types(type->left, block, name);
diff --git a/034call.cc b/034call.cc
index 80d142d7..957a43f6 100644
--- a/034call.cc
+++ b/034call.cc
@@ -96,7 +96,7 @@ inline const instruction& to_instruction(const call& call) {
 
 :(after "Defined Recipe Checks")
 // not a primitive; check that it's present in the book of recipes
-if (Recipe.find(inst.operation) == Recipe.end()) {
+if (!contains_key(Recipe, inst.operation)) {
   raise_error << maybe(get(Recipe, r).name) << "undefined operation in '" << inst.to_string() << "'\n" << end();
   break;
 }
diff --git a/041jump_target.cc b/041jump_target.cc
index d7ff717a..3bd8cedb 100644
--- a/041jump_target.cc
+++ b/041jump_target.cc
@@ -27,7 +27,7 @@ void transform_labels(const recipe_ordinal r) {
   for (long long int i = 0; i < SIZE(get(Recipe, r).steps); ++i) {
     const instruction& inst = get(Recipe, r).steps.at(i);
     if (!inst.label.empty() && inst.label.at(0) == '+') {
-      if (offset.find(inst.label) == offset.end()) {
+      if (!contains_key(offset, inst.label)) {
         offset[inst.label] = i;
       }
       else {
@@ -71,7 +71,7 @@ void replace_offset(reagent& x, /*const*/ map<string, long long int>& offset, co
     x.set_value(0);  // no jump by default
     return;
   }
-  if (offset.find(x.name) == offset.end()) {
+  if (!contains_key(offset, x.name)) {
     raise_error << maybe(get(Recipe, r).name) << "can't find label " << x.name << '\n' << end();
     x.set_value(0);  // no jump by default
     return;
diff --git a/042name.cc b/042name.cc
index ae540c57..d38bda4c 100644
--- a/042name.cc
+++ b/042name.cc
@@ -80,7 +80,7 @@ bool disqualified(/*mutable*/ reagent& x, const instruction& inst, const string&
 }
 
 bool already_transformed(const reagent& r, const map<string, long long int>& names) {
-  return names.find(r.name) != names.end();
+  return contains_key(names, r.name);
 }
 
 long long int lookup_name(const reagent& r, const recipe_ordinal default_recipe) {
diff --git a/046closure_name.cc b/046closure_name.cc
index 70c3481e..3d8e2e00 100644
--- a/046closure_name.cc
+++ b/046closure_name.cc
@@ -65,7 +65,7 @@ void collect_surrounding_spaces(const recipe_ordinal r) {
       }
       if (s->right) raise_error << "slot 0 should have a single value in /names, but got " << inst.products.at(j).to_string() << '\n' << end();
       const string& surrounding_recipe_name = s->value;
-      if (Surrounding_space.find(r) != Surrounding_space.end()
+      if (contains_key(Surrounding_space, r)
           && Surrounding_space[r] != get(Recipe_ordinal, surrounding_recipe_name)) {
         raise_error << "recipe " << get(Recipe, r).name << " can have only one 'surrounding' recipe but has " << Recipe[Surrounding_space[r]].name << " and " << surrounding_recipe_name << '\n' << end();
         continue;
@@ -99,7 +99,7 @@ long long int lookup_name(const reagent& x, const recipe_ordinal default_recipe)
 // recursively call transform_names on it.
 long long int lookup_name(const reagent& x, const recipe_ordinal r, set<recipe_ordinal>& done, vector<recipe_ordinal>& path) {
   if (!Name[r].empty()) return Name[r][x.name];
-  if (done.find(r) != done.end()) {
+  if (contains_key(done, r)) {
     raise_error << "can't compute address of " << x.to_string() << " because " << end();
     for (long long int i = 1; i < SIZE(path); ++i) {
       raise_error << path.at(i-1) << " requires computing names of " << path.at(i) << '\n' << end();
@@ -116,7 +116,7 @@ long long int lookup_name(const reagent& x, const recipe_ordinal r, set<recipe_o
 
 recipe_ordinal lookup_surrounding_recipe(const recipe_ordinal r, long long int n) {
   if (n == 0) return r;
-  if (Surrounding_space.find(r) == Surrounding_space.end()) {
+  if (!contains_key(Surrounding_space, r)) {
     raise_error << "don't know surrounding recipe of " << get(Recipe, r).name << '\n' << end();
     return 0;
   }
@@ -135,5 +135,5 @@ bool already_transformed(const reagent& r, const map<string, long long int>& nam
     }
     if (p->value != "0") return true;
   }
-  return names.find(r.name) != names.end();
+  return contains_key(names, r.name);
 }
diff --git a/048check_type_by_name.cc b/048check_type_by_name.cc
index a3deba6c..79328427 100644
--- a/048check_type_by_name.cc
+++ b/048check_type_by_name.cc
@@ -41,11 +41,11 @@ void check_type(map<string, type_tree*>& type, map<string, string_tree*>& type_n
   // if you use raw locations you're probably doing something unsafe
   if (is_integer(x.name)) return;
   if (!x.type) return;  // will throw a more precise error elsewhere
-  if (type.find(x.name) == type.end()) {
+  if (!contains_key(type, x.name)) {
     trace(9992, "transform") << x.name << " => " << dump_types(x) << end();
     type[x.name] = x.type;
   }
-  if (type_name.find(x.name) == type_name.end()) {
+  if (!contains_key(type_name, x.name)) {
     type_name[x.name] = x.properties.at(0).second;
   }
   if (!types_match(type[x.name], x.type))
@@ -61,7 +61,7 @@ recipe main [
 :(code)
 void deduce_missing_type(map<string, type_tree*>& type, map<string, string_tree*>& type_name, reagent& x) {
   if (x.type) return;
-  if (type.find(x.name) == type.end()) return;
+  if (!contains_key(type, x.name)) return;
   x.type = new type_tree(*type[x.name]);
   trace(9992, "transform") << x.name << " <= " << dump_types(x) << end();
   assert(!x.properties.at(0).second);
diff --git a/050scenario.cc b/050scenario.cc
index e60ee771..0a1c0f90 100644
--- a/050scenario.cc
+++ b/050scenario.cc
@@ -74,7 +74,7 @@ else if (command == "scenario") {
 scenario parse_scenario(istream& in) {
   scenario result;
   result.name = next_word(in);
-  if (Scenario_names.find(result.name) != Scenario_names.end())
+  if (contains_key(Scenario_names, result.name))
     raise_error << "duplicate scenario name: " << result.name << '\n' << end();
   Scenario_names.insert(result.name);
   skip_whitespace_and_comments(in);
@@ -281,7 +281,7 @@ void check_memory(const string& s) {
     string _assign;  in >> _assign;  assert(_assign == "<-");
     skip_whitespace_and_comments(in);
     double value = 0;  in >> value;
-    if (locations_checked.find(address) != locations_checked.end())
+    if (contains_key(locations_checked, address))
       raise_error << "duplicate expectation for location " << address << '\n' << end();
     trace(9999, "run") << "checking location " << address << end();
     if (get_or_insert(Memory, address) != value) {
diff --git a/052tangle.cc b/052tangle.cc
index c3bc7e46..c9f9f28c 100644
--- a/052tangle.cc
+++ b/052tangle.cc
@@ -84,11 +84,11 @@ void insert_fragments(const recipe_ordinal r) {
       Fragments_used.insert(inst.label);
       ostringstream prefix;
       prefix << '+' << get(Recipe, r).name << '_' << pass << '_' << i;
-      if (Before_fragments.find(inst.label) != Before_fragments.end()) {
+      if (contains_key(Before_fragments, inst.label)) {
         append_fragment(result, Before_fragments[inst.label].steps, prefix.str());
       }
       result.push_back(inst);
-      if (After_fragments.find(inst.label) != After_fragments.end()) {
+      if (contains_key(After_fragments, inst.label)) {
         append_fragment(result, After_fragments[inst.label].steps, prefix.str());
       }
     }
@@ -113,7 +113,7 @@ void append_fragment(vector<instruction>& base, const vector<instruction>& patch
   for (long long int i = 0; i < SIZE(patch); ++i) {
     instruction inst = patch.at(i);
     if (inst.is_label) {
-      if (jump_targets.find(inst.label) != jump_targets.end())
+      if (contains_key(jump_targets, inst.label))
         inst.label = prefix+inst.label;
       base.push_back(inst);
       continue;
@@ -121,7 +121,7 @@ void append_fragment(vector<instruction>& base, const vector<instruction>& patch
     for (long long int j = 0; j < SIZE(inst.ingredients); ++j) {
       reagent& x = inst.ingredients.at(j);
       if (!is_literal(x)) continue;
-      if (x.properties.at(0).second->value == "label" && jump_targets.find(x.name) != jump_targets.end())
+      if (x.properties.at(0).second->value == "label" && contains_key(jump_targets, x.name))
         x.name = prefix+x.name;
     }
     base.push_back(inst);
@@ -142,11 +142,11 @@ void check_insert_fragments(unused recipe_ordinal) {
   if (Transform_check_insert_fragments_Ran) return;
   Transform_check_insert_fragments_Ran = true;
   for (map<string, recipe>::iterator p = Before_fragments.begin(); p != Before_fragments.end(); ++p) {
-    if (Fragments_used.find(p->first) == Fragments_used.end())
+    if (!contains_key(Fragments_used, p->first))
       raise_error << "could not locate insert before " << p->first << '\n' << end();
   }
   for (map<string, recipe>::iterator p = After_fragments.begin(); p != After_fragments.end(); ++p) {
-    if (Fragments_used.find(p->first) == Fragments_used.end())
+    if (!contains_key(Fragments_used, p->first))
       raise_error << "could not locate insert after " << p->first << '\n' << end();
   }
 }
diff --git a/054dilated_reagent.cc b/054dilated_reagent.cc
index 5ac1c97e..fd5fb8c7 100644
--- a/054dilated_reagent.cc
+++ b/054dilated_reagent.cc
@@ -84,7 +84,7 @@ if (s.at(0) == '{') {
   // structures for the first row of properties
   name = properties.at(0).first;
   string type_name = properties.at(0).second->value;
-  if (Type_ordinal.find(type_name) == Type_ordinal.end()) {
+  if (!contains_key(Type_ordinal, type_name)) {
       // this type can't be an integer literal
     put(Type_ordinal, type_name, Next_type_ordinal++);
   }
diff --git a/057static_dispatch.cc b/057static_dispatch.cc
index 905cbaf2..597ef4d0 100644
--- a/057static_dispatch.cc
+++ b/057static_dispatch.cc
@@ -28,7 +28,7 @@ for (map<string, vector<recipe_ordinal> >::iterator p = Recipe_variants.begin();
 }
 
 :(before "End Load Recipe Header(result)")
-if (Recipe_ordinal.find(result.name) != Recipe_ordinal.end()) {
+if (contains_key(Recipe_ordinal, result.name)) {
   if ((Recipe.find(get(Recipe_ordinal, result.name)) == Recipe.end()
           || get(Recipe, get(Recipe_ordinal, result.name)).has_header)
       && !header_already_exists(result)) {
@@ -113,7 +113,7 @@ void resolve_ambiguous_calls(recipe_ordinal r) {
   for (long long int index = 0; index < SIZE(get(Recipe, r).steps); ++index) {
     instruction& inst = get(Recipe, r).steps.at(index);
     if (inst.is_label) continue;
-    if (Recipe_variants.find(inst.name) == Recipe_variants.end()) continue;
+    if (!contains_key(Recipe_variants, inst.name)) continue;
     assert(!Recipe_variants[inst.name].empty());
     replace_best_variant(inst);
   }
diff --git a/058generic_container.cc b/058generic_container.cc
index 843a89c3..44762f00 100644
--- a/058generic_container.cc
+++ b/058generic_container.cc
@@ -50,7 +50,7 @@ void read_type_ingredients(string& name) {
   string save_name = name;
   istringstream in(save_name);
   name = slurp_until(in, ':');
-  if (Type_ordinal.find(name) == Type_ordinal.end() || get(Type_ordinal, name) == 0)
+  if (!contains_key(Type_ordinal, name) || get(Type_ordinal, name) == 0)
     put(Type_ordinal, name, Next_type_ordinal++);
   type_info& info = get_or_insert(Type, get(Type_ordinal, name));
   long long int next_type_ordinal = START_TYPE_INGREDIENTS;
diff --git a/059generic_recipe.cc b/059generic_recipe.cc
index 106d5a14..29850848 100644
--- a/059generic_recipe.cc
+++ b/059generic_recipe.cc
@@ -122,11 +122,11 @@ bool is_type_ingredient_name(const string& type) {
 recipe_ordinal new_variant(recipe_ordinal exemplar, const instruction& inst) {
   string new_name = next_unused_recipe_name(inst.name);
   trace(9993, "transform") << "switching " << inst.name << " to " << new_name << end();
-  assert(Recipe_ordinal.find(new_name) == Recipe_ordinal.end());
+  assert(!contains_key(Recipe_ordinal, new_name));
   recipe_ordinal result = put(Recipe_ordinal, new_name, Next_recipe_ordinal++);
   // make a copy
-  assert(Recipe.find(exemplar) != Recipe.end());
-  assert(Recipe.find(result) == Recipe.end());
+  assert(contains_key(Recipe, exemplar));
+  assert(!contains_key(Recipe, result));
   recently_added_recipes.push_back(result);
   put(Recipe, result, get(Recipe, exemplar));
   recipe& new_recipe = get(Recipe, result);
@@ -165,7 +165,7 @@ void accumulate_type_ingredients(const string_tree* base, const string_tree* ref
   }
   if (!base->value.empty() && base->value.at(0) == '_') {
     assert(!refinement->value.empty());
-    if (mappings.find(base->value) == mappings.end()) {
+    if (!contains_key(mappings, base->value)) {
       trace(9993, "transform") << "adding mapping from " << base->value << " to " << refinement->value << end();
       mappings[base->value] = refinement->value;
     }
@@ -217,7 +217,7 @@ void replace_type_ingredients(reagent& x, const map<string, string>& mappings) {
 
 void replace_type_ingredients(string_tree* type, const map<string, string>& mappings) {
   if (!type) return;
-  if (is_type_ingredient_name(type->value) && mappings.find(type->value) != mappings.end()) {
+  if (is_type_ingredient_name(type->value) && contains_key(mappings, type->value)) {
     trace(9993, "transform") << type->value << " => " << mappings.find(type->value)->second << end();
     type->value = mappings.find(type->value)->second;
   }
diff --git a/075scenario_console.cc b/075scenario_console.cc
index 4ed1d583..ab07ad76 100644
--- a/075scenario_console.cc
+++ b/075scenario_console.cc
@@ -72,7 +72,7 @@ case ASSUME_CONSOLE: {
       string key = curr.ingredients.at(0).name;
       if (is_integer(key))
         put(Memory, Current_routine->alloc+1, to_integer(key));
-      else if (Key.find(key) != Key.end())
+      else if (contains_key(Key, key))
         put(Memory, Current_routine->alloc+1, Key[key]);
       else
         raise_error << "assume-console: can't press " << key << '\n' << end();
diff --git a/080trace_browser.cc b/080trace_browser.cc
index 26c856eb..676be4f2 100644
--- a/080trace_browser.cc
+++ b/080trace_browser.cc
@@ -78,7 +78,7 @@ void start_trace_browser() {
       for (int screen_row = tb_height(); screen_row > 0 && Top_of_screen > 0; --screen_row) {
         --Top_of_screen;
         if (Top_of_screen <= 0) break;
-        while (Top_of_screen > 0 && Visible.find(Top_of_screen) == Visible.end())
+        while (Top_of_screen > 0 && !contains_key(Visible, Top_of_screen))
           --Top_of_screen;
       }
       if (Top_of_screen > 0)
@@ -90,7 +90,7 @@ void start_trace_browser() {
       for (int screen_row = tb_height(); screen_row > 0 && Top_of_screen > 0; --screen_row) {
         --Top_of_screen;
         if (Top_of_screen <= 0) break;
-        while (Top_of_screen > 0 && Visible.find(Top_of_screen) == Visible.end())
+        while (Top_of_screen > 0 && !contains_key(Visible, Top_of_screen))
           --Top_of_screen;
       }
       refresh_screen_rows();
@@ -100,13 +100,13 @@ void start_trace_browser() {
     }
     if (key == TB_KEY_CARRIAGE_RETURN) {
       // expand lines under current by one level
-      assert(Trace_index.find(Display_row) != Trace_index.end());
+      assert(contains_key(Trace_index, Display_row));
       long long int start_index = Trace_index[Display_row];
       long long int index = 0;
       // simultaneously compute end_index and min_depth
       int min_depth = 9999;
       for (index = start_index+1; index < SIZE(Trace_stream->past_lines); ++index) {
-        if (Visible.find(index) != Visible.end()) break;
+        if (contains_key(Visible, index)) break;
         trace_line& curr_line = Trace_stream->past_lines.at(index);
         if (curr_line.depth == 0) continue;
         assert(curr_line.depth > Trace_stream->past_lines.at(start_index).depth);
@@ -124,13 +124,13 @@ void start_trace_browser() {
     }
     if (key == TB_KEY_BACKSPACE || key == TB_KEY_BACKSPACE2) {
       // collapse all lines under current
-      assert(Trace_index.find(Display_row) != Trace_index.end());
+      assert(contains_key(Trace_index, Display_row));
       long long int start_index = Trace_index[Display_row];
       long long int index = 0;
       // end_index is the next line at a depth same as or lower than start_index
       int initial_depth = Trace_stream->past_lines.at(start_index).depth;
       for (index = start_index+1; index < SIZE(Trace_stream->past_lines); ++index) {
-        if (Visible.find(index) == Visible.end()) continue;
+        if (!contains_key(Visible, index)) continue;
         trace_line& curr_line = Trace_stream->past_lines.at(index);
         if (curr_line.depth == 0) continue;
         if (curr_line.depth <= initial_depth) break;
@@ -152,7 +152,7 @@ void refresh_screen_rows() {
   Trace_index.clear();
   for (screen_row = 0, index = Top_of_screen; screen_row < tb_height() && index < SIZE(Trace_stream->past_lines); ++screen_row, ++index) {
     // skip lines without depth for now
-    while (Visible.find(index) == Visible.end()) {
+    while (!contains_key(Visible, index)) {
       ++index;
       if (index >= SIZE(Trace_stream->past_lines)) goto done;
     }
@@ -165,7 +165,7 @@ done:;
 void render() {
   long long int screen_row = 0;
   for (screen_row = 0; screen_row < tb_height(); ++screen_row) {
-    if (Trace_index.find(screen_row) == Trace_index.end()) break;
+    if (!contains_key(Trace_index, screen_row)) break;
     trace_line& curr_line = Trace_stream->past_lines.at(Trace_index[screen_row]);
     ostringstream out;
     out << std::setw(4) << curr_line.depth << ' ' << curr_line.label << ": " << curr_line.contents;
@@ -189,8 +189,8 @@ void render() {
 }
 
 long long int lines_hidden(long long int screen_row) {
-  assert(Trace_index.find(screen_row) != Trace_index.end());
-  if (Trace_index.find(screen_row+1) == Trace_index.end())
+  assert(contains_key(Trace_index, screen_row));
+  if (!contains_key(Trace_index, screen_row+1))
     return SIZE(Trace_stream->past_lines)-Trace_index[screen_row];
   else
     return Trace_index[screen_row+1] - Trace_index[screen_row];
diff --git a/081run_interactive.cc b/081run_interactive.cc
index 68225d3c..f871275a 100644
--- a/081run_interactive.cc
+++ b/081run_interactive.cc
@@ -69,7 +69,7 @@ Track_most_recent_products = false;
 // all warnings.
 // returns true if successfully called (no errors found during load and transform)
 bool run_interactive(long long int address) {
-  assert(Recipe_ordinal.find("interactive") != Recipe_ordinal.end() && get(Recipe_ordinal, "interactive") != 0);
+  assert(contains_key(Recipe_ordinal, "interactive") && get(Recipe_ordinal, "interactive") != 0);
   // try to sandbox the run as best you can
   // todo: test this
   if (!Current_scenario) {