Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 13 additions & 0 deletions include/ygm/container/bag.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
#include <initializer_list>
#include <ygm/container/container_traits.hpp>
#include <ygm/container/detail/base_async_insert.hpp>
#include <ygm/container/detail/base_contains.hpp>
#include <ygm/container/detail/base_count.hpp>
#include <ygm/container/detail/base_iteration.hpp>
#include <ygm/container/detail/base_iterators.hpp>
Expand All @@ -28,6 +29,7 @@ namespace ygm::container {
*/
template <typename Item>
class bag : public detail::base_async_insert_value<bag<Item>, std::tuple<Item>>,
public detail::base_contains<bag<Item>, std::tuple<Item>>,
public detail::base_count<bag<Item>, std::tuple<Item>>,
public detail::base_misc<bag<Item>, std::tuple<Item>>,
public detail::base_iterators<bag<Item>>,
Expand Down Expand Up @@ -259,6 +261,17 @@ class bag : public detail::base_async_insert_value<bag<Item>, std::tuple<Item>>,
return std::count(m_local_bag.begin(), m_local_bag.end(), val);
}

/**
* @brief Check if a value exists locally
*
* @param val Value to check for
* @return True if value exists locally, false otherwise
*/
bool local_contains(const value_type &val) const {
return std::find(m_local_bag.begin(), m_local_bag.end(), val) !=
m_local_bag.end();
}

/**
* @brief Execute a functor on every locally-held item
*
Expand Down
12 changes: 12 additions & 0 deletions include/ygm/container/counting_set.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@

#include <ygm/comm.hpp>
#include <ygm/container/container_traits.hpp>
#include <ygm/container/detail/base_contains.hpp>
#include <ygm/container/detail/base_count.hpp>
#include <ygm/container/detail/base_iteration.hpp>
#include <ygm/container/detail/base_misc.hpp>
Expand All @@ -25,6 +26,7 @@ namespace ygm::container {
template <typename Key>
class counting_set
: public detail::base_count<counting_set<Key>, std::tuple<Key, size_t>>,
public detail::base_contains<counting_set<Key>, std::tuple<Key, size_t>>,
public detail::base_misc<counting_set<Key>, std::tuple<Key, size_t>>,
public detail::base_iterators<counting_set<Key>>,
public detail::base_iteration_key_value<counting_set<Key>,
Expand Down Expand Up @@ -286,6 +288,16 @@ class counting_set
return local_count;
}

/**
* @brief Check if a locally-held item exists
*
* @param val Value to check for
* @return true if value exists locally, false otherwise
*/
bool local_contains(const key_type &key) const {
return m_map.local_contains(key);
}

/**
* @brief Count the total number of items counted
*
Expand Down
35 changes: 35 additions & 0 deletions include/ygm/container/detail/base_contains.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
// Copyright 2019-2025 Lawrence Livermore National Security, LLC and other YGM
// Project Developers. See the top-level COPYRIGHT file for details.
//
// SPDX-License-Identifier: MIT

#pragma once

#include <tuple>
#include <utility>

namespace ygm::container::detail {

/**
* @brief Curiously-recurring template parameter struct that provides
* count operation
*/
template <typename derived_type, typename for_all_args>
struct base_contains {
/**
* @brief Checks for the presence of a value within a container.
*
* @param value Value to search for within container (key in the case of
* containers with keys)
* @return True if `value` exists in container; false otherwise.
*/
bool contains(
const typename std::tuple_element<0, for_all_args>::type& value) const {
const derived_type* derived_this = static_cast<const derived_type*>(this);
derived_this->comm().barrier();
return ::ygm::logical_or(derived_this->local_contains(value),
derived_this->comm());
}
};

} // namespace ygm::container::detail
12 changes: 12 additions & 0 deletions include/ygm/container/map.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
#include <ygm/container/detail/base_async_reduce.hpp>
#include <ygm/container/detail/base_async_visit.hpp>
#include <ygm/container/detail/base_batch_erase.hpp>
#include <ygm/container/detail/base_contains.hpp>
#include <ygm/container/detail/base_count.hpp>
#include <ygm/container/detail/base_iteration.hpp>
#include <ygm/container/detail/base_iterators.hpp>
Expand All @@ -28,6 +29,7 @@ class map
public detail::base_async_insert_or_assign<map<Key, Value>,
std::tuple<Key, Value>>,
public detail::base_misc<map<Key, Value>, std::tuple<Key, Value>>,
public detail::base_contains<map<Key, Value>, std::tuple<Key, Value>>,
public detail::base_count<map<Key, Value>, std::tuple<Key, Value>>,
public detail::base_async_reduce<map<Key, Value>, std::tuple<Key, Value>>,
public detail::base_async_erase_key<map<Key, Value>,
Expand Down Expand Up @@ -562,6 +564,16 @@ class map
return m_local_map.count(key);
}

/**
* @brief Check if a key exists locally
*
* @param key key to check for
* @return True if `key` exists locally, false otherwise
*/
bool local_contains(const key_type& key) const {
return m_local_map.contains(key);
}

// void serialize(const std::string& fname) { m_impl.serialize(fname); }
// void deserialize(const std::string& fname) { m_impl.deserialize(fname); }

Expand Down
12 changes: 12 additions & 0 deletions include/ygm/container/set.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
#include <ygm/container/detail/base_async_insert.hpp>
#include <ygm/container/detail/base_async_insert_contains.hpp>
#include <ygm/container/detail/base_batch_erase.hpp>
#include <ygm/container/detail/base_contains.hpp>
#include <ygm/container/detail/base_count.hpp>
#include <ygm/container/detail/base_iteration.hpp>
#include <ygm/container/detail/base_iterators.hpp>
Expand All @@ -27,6 +28,7 @@ class set
public detail::base_batch_erase_key<set<Value>, std::tuple<Value>>,
public detail::base_async_contains<set<Value>, std::tuple<Value>>,
public detail::base_async_insert_contains<set<Value>, std::tuple<Value>>,
public detail::base_contains<set<Value>, std::tuple<Value>>,
public detail::base_count<set<Value>, std::tuple<Value>>,
public detail::base_misc<set<Value>, std::tuple<Value>>,
public detail::base_iterators<set<Value>>,
Expand Down Expand Up @@ -228,6 +230,16 @@ class set
return m_local_set.count(val);
}

/**
* @brief Check if a value exists locally
*
* @param val Value to check for
* @return True if value exists locally, false otherwise
*/
bool local_contains(const value_type &val) const {
return m_local_set.contains(val);
}

/**
* @brief Get the number of elements stored on the local process.
*
Expand Down
2 changes: 1 addition & 1 deletion test/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ add_ygm_test(test_set)
add_ygm_test(test_bag)
#add_ygm_test(test_tagged_bag)
add_ygm_test(test_array)
#add_ygm_test(test_counting_set)
# add_ygm_test(test_counting_set)
add_ygm_test(test_disjoint_set)
#add_ygm_test(test_container_serialization)
add_ygm_test(test_line_parser)
Expand Down
12 changes: 12 additions & 0 deletions test/test_bag.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,12 @@ int main(int argc, char** argv) {
YGM_ASSERT_RELEASE(bbag.count("red") == 1);
YGM_ASSERT_RELEASE(bbag.size() == 3);

// test contains.
YGM_ASSERT_RELEASE(bbag.contains("dog"));
YGM_ASSERT_RELEASE(bbag.contains("apple"));
YGM_ASSERT_RELEASE(bbag.contains("red"));
YGM_ASSERT_RELEASE(!bbag.contains("blue"));

for (auto& value : bbag) {
world.cout(value);
}
Expand Down Expand Up @@ -158,6 +164,12 @@ int main(int argc, char** argv) {
YGM_ASSERT_RELEASE(bbag.count("apple") == (size_t)world.size());
YGM_ASSERT_RELEASE(bbag.count("red") == (size_t)world.size());

// test contains
YGM_ASSERT_RELEASE(bbag.contains("dog"));
YGM_ASSERT_RELEASE(bbag.contains("apple"));
YGM_ASSERT_RELEASE(bbag.contains("red"));
YGM_ASSERT_RELEASE(!bbag.contains("blue"));

{
std::vector<std::string> all_data;
bbag.gather(all_data, 0);
Expand Down
24 changes: 24 additions & 0 deletions test/test_counting_set.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,12 @@ int main(int argc, char **argv) {
YGM_ASSERT_RELEASE(count_map["dog"] == 1);
YGM_ASSERT_RELEASE(count_map["apple"] == 1);
YGM_ASSERT_RELEASE(count_map.count("cat") == 0);

// test contains
YGM_ASSERT_RELEASE(cset.contains("dog"));
YGM_ASSERT_RELEASE(cset.contains("apple"));
YGM_ASSERT_RELEASE(cset.contains("red"));
YGM_ASSERT_RELEASE(!cset.contains("blue"));
}

//
Expand All @@ -66,6 +72,12 @@ int main(int argc, char **argv) {
YGM_ASSERT_RELEASE(cset.count("cat") == 0);

YGM_ASSERT_RELEASE(cset.count_all() == 3 * (size_t)world.size());

// test contains
YGM_ASSERT_RELEASE(cset.contains("dog"));
YGM_ASSERT_RELEASE(cset.contains("apple"));
YGM_ASSERT_RELEASE(cset.contains("red"));
YGM_ASSERT_RELEASE(!cset.contains("blue"));
}

//
Expand Down Expand Up @@ -113,6 +125,12 @@ int main(int argc, char **argv) {
YGM_ASSERT_RELEASE(cset.count("dog") == 0);
YGM_ASSERT_RELEASE(cset.count("apple") == 0);
YGM_ASSERT_RELEASE(cset.count("red") == 0);

// test contains
YGM_ASSERT_RELEASE(!cset.contains("dog"));
YGM_ASSERT_RELEASE(!cset.contains("apple"));
YGM_ASSERT_RELEASE(!cset.contains("red"));
YGM_ASSERT_RELEASE(!cset.contains("blue"));
}

// //
Expand Down Expand Up @@ -166,6 +184,12 @@ int main(int argc, char **argv) {
YGM_ASSERT_RELEASE(cset2.count("bird") == (size_t)world.size());
YGM_ASSERT_RELEASE(cset2.count("red") == 0);
YGM_ASSERT_RELEASE(cset2.size() == 3);

// test contains
YGM_ASSERT_RELEASE(cset2.contains("dog"));
YGM_ASSERT_RELEASE(cset2.contains("cat"));
YGM_ASSERT_RELEASE(cset2.contains("bird"));
YGM_ASSERT_RELEASE(!cset2.contains("red"));
}

//
Expand Down
28 changes: 28 additions & 0 deletions test/test_map.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,12 @@ int main(int argc, char **argv) {
YGM_ASSERT_RELEASE(smap.count("dog") == 1);
YGM_ASSERT_RELEASE(smap.count("apple") == 1);
YGM_ASSERT_RELEASE(smap.count("red") == 1);

// test contains.
YGM_ASSERT_RELEASE(smap.contains("dog"));
YGM_ASSERT_RELEASE(smap.contains("apple"));
YGM_ASSERT_RELEASE(smap.contains("red"));
YGM_ASSERT_RELEASE(!smap.contains("blue"));
}

//
Expand All @@ -54,6 +60,12 @@ int main(int argc, char **argv) {
YGM_ASSERT_RELEASE(smap.count("dog") == 1);
YGM_ASSERT_RELEASE(smap.count("apple") == 1);
YGM_ASSERT_RELEASE(smap.count("red") == 1);

// test contains.
YGM_ASSERT_RELEASE(smap.contains("dog"));
YGM_ASSERT_RELEASE(smap.contains("apple"));
YGM_ASSERT_RELEASE(smap.contains("red"));
YGM_ASSERT_RELEASE(!smap.contains("blue"));
}

//
Expand Down Expand Up @@ -135,13 +147,21 @@ int main(int argc, char **argv) {

YGM_ASSERT_RELEASE(smap.size() == 2);

// test contains.
YGM_ASSERT_RELEASE(smap.contains("dog"));
YGM_ASSERT_RELEASE(smap.contains("cat"));
YGM_ASSERT_RELEASE(!smap.contains("red"));
YGM_ASSERT_RELEASE(!smap.contains("blue"));

if (world.rank() == 0) {
smap.async_erase("dog");
}
YGM_ASSERT_RELEASE(smap.count("dog") == 0);
YGM_ASSERT_RELEASE(smap.size() == 1);
YGM_ASSERT_RELEASE(!smap.contains("dog"));
smap.async_erase("cat");
YGM_ASSERT_RELEASE(smap.count("cat") == 0);
YGM_ASSERT_RELEASE(!smap.contains("cat"));

YGM_ASSERT_RELEASE(smap.size() == 0);
}
Expand Down Expand Up @@ -259,9 +279,17 @@ int main(int argc, char **argv) {
YGM_ASSERT_RELEASE(smap.count("dog") == 1);
YGM_ASSERT_RELEASE(smap.count("apple") == 1);
YGM_ASSERT_RELEASE(smap.count("red") == 1);

YGM_ASSERT_RELEASE(!smap.contains("car"));
smap.async_insert_or_assign("car", "truck");
YGM_ASSERT_RELEASE(smap.size() == 4);
YGM_ASSERT_RELEASE(smap.count("car") == 1);

// test contains.
YGM_ASSERT_RELEASE(smap.contains("dog"));
YGM_ASSERT_RELEASE(smap.contains("car"));
YGM_ASSERT_RELEASE(smap.contains("red"));
YGM_ASSERT_RELEASE(!smap.contains("blue"));
}

// Test batch erase from set
Expand Down
Loading