unordered_set unordered_map unordered example c++ c++11 unordered-map

c++ - example - El método más simple para verificar si unordered_map de unordered_maps contiene la clave



unordered_map c++ example (5)

¿Algo como esto? (para el caso mutable)

using inner_map = std::map<key_type, value_type>; using outer_map = std::map<key_type, inner_map> boost::optional<value_type&> element_for_keys(outer_map& map, const key_type& k1, const key_type& k2) { auto it_outer = map.find(k1); if (it_outer = map.end()) return {}; auto &map2 = it_outer->second; auto it_inner = map2.find(k2); if (it_inner == map2.end()) return {}; return { it_inner->second }; }

llamado así

auto op_value = element_for_keys(my_map, kv1, kv2); if (op_value) { // use op_value.value() } else { // handle case where it does not exist }

... o hay una forma más parecida a la pitón ...

try { auto& v = my_map.at(k1).at(k2); // use v } catch(const std::out_of_range & e) { // didn''t find it }

Estoy usando un mapa desordenado de mapas desordenados, de manera que puedo hacer referencia a un elemento usando la sintaxis de "clave múltiple"

my_map[k1][k2] .

¿Hay alguna forma conveniente de usar la misma sintaxis de "clave múltiple" para verificar si existe un elemento antes de intentar acceder a él? Si no, ¿cuál es la forma más sencilla?


No creo que haya una sintaxis de claves múltiples para verificar, pero la forma más sencilla sería usar el método de find . Podrías escribir una función simple para aplicarla a un unordered_map de un unordered_map unordered_map

std::unordered_map::find


Si su intención es probar la existencia de la clave, no usaría

my_map[k1][k2]

porque el operator[] creará por defecto un nuevo valor para esa clave si aún no existe.

Más bien preferiría usar std::unordered_map::find . Entonces, si está seguro de que existe la primera clave, pero no la segunda, podría hacerlo.

if (my_map[k1].find(k2) != my_map[k1].end()) { // k2 exists in unordered_map for key k1 }

Si desea realizar una función que compruebe la existencia de ambas claves, podría escribir algo como

//------------------------------------------------------------------------------ /// /brief Determines a nested map contains two keys (the outer containing the inner) /// /param[in] data Outer-most map /// /param[in] a Key used to find the inner map /// /param[in] b Key used to find the value within the inner map /// /return True if both keys exist, false otherwise //------------------------------------------------------------------------------ template <class key_t, class value_t> bool nested_key_exists(std::unordered_map<key_t, std::unordered_map<key_t, value_t>> const& data, key_t const a, key_t const b) { auto itInner = data.find(a); if (itInner != data.end()) { return itInner->second.find(b) != itInner->second.end(); } return false; }



template<class M> bool contains(M const&){return true;} template<class M, class K, class...Ks> bool contains(M const&m, K const&k, Ks const&...ks){ auto it=m.find(k); if (it==m.end()) return false; return contains(it->second, ks...); }

Trabajará para cada contenedor asociativo de un solo valor.

contains(my_map, k1, k2) es verdadero si hay un elemento k1 que contiene k2 .