6#include <unordered_map>
8#include "testing/testing.h"
21TEST(map, DefaultConstructor)
61TEST(map, ItemsConstructorDuplicates)
63 Map<int, int> map = {{1, 2}, {3, 4}, {1, 4}, {2, 5}, {2, 6}};
114 for (
int i = 0;
i < 100;
i++) {
143 std::optional<int> value = map.
pop_try(4);
145 EXPECT_FALSE(value.has_value());
148 EXPECT_TRUE(value.has_value());
176 for (
int i = 0;
i < 100;
i++) {
179 for (
int i = 25;
i < 80;
i++) {
182 for (
int i = 0;
i < 100;
i++) {
197 for (
float value : map.
values()) {
204 EXPECT_TRUE(values.
contains(-2.0f));
218 for (
int key : map.
keys()) {
241 for (
auto item : const_map.
items()) {
243 values.
add(item.value);
262 for (
int &value : map.
values()) {
276 for (
auto item : map.
items()) {
277 item.value += item.key;
284TEST(map, MutableItemToItemConversion)
293 values.
append(item.value);
309TEST(map, LookupOrAddCB_SeparateFunction)
318TEST(map, LookupOrAddCB_Lambdas)
321 auto lambda1 = []() {
return 11.0f; };
323 auto lambda2 = []() {
return 20.0f; };
337 auto modify_func = [](
float *value) {
350 auto create_func = [](std::unique_ptr<int> *value) ->
int & {
351 new (value) std::unique_ptr<int>(
new int{10});
354 auto modify_func = [](std::unique_ptr<int> *value) ->
int & {
373 EXPECT_FALSE(map.
add(3, 8.0f));
423 for (
int i = 0;
i < 100;
i++) {
440 map2 = std::move(map1);
481 auto value1 = std::make_unique<int>();
482 auto value2 = std::make_unique<int>();
483 auto value3 = std::make_unique<int>();
485 int *value1_ptr = value1.get();
488 map.
add_new(1, std::move(value1));
489 map.
add(2, std::move(value2));
492 map.
add_new(5, std::make_unique<int>());
493 map.
add(6, std::make_unique<int>());
507 EXPECT_FALSE(map.
remove(3));
509 EXPECT_TRUE(map.
remove(2));
518 EXPECT_TRUE(map.
add(&a, 5));
519 EXPECT_FALSE(map.
add(&a, 4));
524 EXPECT_TRUE(map.
add(&
b, 8));
525 EXPECT_FALSE(map.
remove(&d));
526 EXPECT_TRUE(map.
remove(&a));
528 EXPECT_TRUE(map.
remove(&c));
536 map.
add(
"45",
"643");
560TEST(map, CopyConstructorExceptions)
566 map.lookup(2).throw_during_copy =
true;
567 EXPECT_ANY_THROW({ MapType map_copy(map); });
570TEST(map, MoveConstructorExceptions)
576 map.lookup(1).throw_during_move =
true;
577 EXPECT_ANY_THROW({ MapType map_moved(std::move(map)); });
587 EXPECT_ANY_THROW({ map.
add_new(key1, value1); });
592 EXPECT_ANY_THROW({ map.
add_new(key2, value2); });
601 map.
lookup(2).throw_during_move =
true;
602 EXPECT_ANY_THROW({ map.
reserve(100); });
611 map.
lookup(3).throw_during_move =
true;
612 EXPECT_ANY_THROW({ map.
pop(3); });
618TEST(map, AddOrModifyExceptions)
623 EXPECT_ANY_THROW({ map.
add_or_modify(3, create_fn, modify_fn); });
638 map.
add(TestEnum::A, 4);
639 map.
add(TestEnum::B, 6);
643 EXPECT_FALSE(map.
contains(TestEnum::C));
644 map.
lookup(TestEnum::D) = 10;
656 EXPECT_TRUE(std::any_of(map.
keys().
begin(), map.
keys().
end(), [](
int v) { return v == 1; }));
658 EXPECT_TRUE(std::any_of(
668 map.
add_as(3,
"hello", 2);
674TEST(map, RemoveDuringIteration)
688 for (Iter iter =
begin; iter != end; ++iter) {
690 if (item.
value == 2) {
707 const int64_t removed = map.
remove_if([](
auto item) {
return item.key > 100; });
735 map.
add({1, 2, 3}, 100);
736 map.
add({3, 2, 1}, 200);
743 std::array<int, 3>
array = {1, 2, 3};
769 std::string value =
"a";
770 bool value_checked =
false;
773 value_checked =
true;
776 EXPECT_TRUE(value_checked);
784template<
typename MapT>
789 for (
int i = 0;
i < amount;
i++) {
797 for (
int value : values) {
798 map.add(value, value);
804 for (
int value : values) {
805 count += map.contains(value);
810 for (
int value : values) {
811 count += map.remove(value);
816 std::cout <<
"Count: " <<
count <<
"\n";
823template<
typename Key,
typename Value>
class StdUnorderedMapWrapper {
825 using MapType = std::unordered_map<Key, Value, blender::DefaultHash<Key>>;
834 bool is_empty()
const
844 template<
typename ForwardKey,
typename... ForwardValue>
845 void add_new(ForwardKey &&key, ForwardValue &&...value)
847 map_.insert({std::forward<ForwardKey>(key),
Value(std::forward<ForwardValue>(value)...)});
850 template<
typename ForwardKey,
typename... ForwardValue>
851 bool add(ForwardKey &&key, ForwardValue &&...value)
854 .insert({std::forward<ForwardKey>(key),
Value(std::forward<ForwardValue>(value)...)})
860 return map_.find(key) != map_.end();
865 return bool(map_.erase(key));
870 return map_.find(key)->second;
875 return map_.find(key)->second;
883 void print_stats(StringRef =
"")
const {}
888 for (
int i = 0;
i < 3;
i++) {
889 benchmark_random_ints<blender::Map<int, int>>(
"blender::Map ", 1000000, 1);
890 benchmark_random_ints<blender::StdUnorderedMapWrapper<int, int>>(
891 "std::unordered_map", 1000000, 1);
894 for (
int i = 0;
i < 3;
i++) {
896 benchmark_random_ints<blender::Map<int, int>>(
"blender::Map ", 1000000, factor);
897 benchmark_random_ints<blender::StdUnorderedMapWrapper<int, int>>(
898 "std::unordered_map", 1000000, factor);
EXPECT_EQ(BLI_expr_pylike_eval(expr, nullptr, 0, &result), EXPR_PYLIKE_INVALID)
void int BLI_rng_get_int(struct RNG *rng) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
struct RNG * BLI_rng_new(unsigned int seed)
void BLI_rng_free(struct RNG *rng) ATTR_NONNULL(1)
#define SCOPED_TIMER(name)
ATTR_WARN_UNUSED_RESULT const BMVert * v
static DBVT_INLINE btScalar size(const btDbvtVolume &a)
SubIterator begin() const
const Value * lookup_ptr(const Key &key) const
Value pop(const Key &key)
std::optional< Value > lookup_try(const Key &key) const
std::optional< Value > pop_try(const Key &key)
Value & lookup_or_add_default(const Key &key)
const Key & lookup_key_as(const ForwardKey &key) const
bool remove_as(const ForwardKey &key)
bool add_overwrite(const Key &key, const Value &value)
ValueIterator values() const &
bool add(const Key &key, const Value &value)
const Value & lookup(const Key &key) const
const Key * lookup_key_ptr_as(const ForwardKey &key) const
Value & lookup_or_add_cb(const Key &key, const CreateValueF &create_value)
void foreach_item(const FuncT &func) const
const Key & lookup_key(const Key &key) const
bool add_as(ForwardKey &&key, ForwardValue &&...value)
const Key * lookup_key_ptr(const Key &key) const
void add_new(const Key &key, const Value &value)
const Value & lookup_as(const ForwardKey &key) const
bool remove(const Key &key)
KeyIterator keys() const &
bool contains(const Key &key) const
auto add_or_modify(const Key &key, const CreateValueF &create_value, const ModifyValueF &modify_value) -> decltype(create_value(nullptr))
int64_t remove_if(Predicate &&predicate)
Value pop_default(const Key &key, const Value &default_value)
ItemIterator items() const &
Value & lookup_or_add(const Key &key, const Value &value)
bool contains(const Key &key) const
bool contains(const T &value) const
void append(const T &value)
int64_t first_index_of(const T &value) const
MutableSpan< T > as_mutable_span()
static void clear(Message &msg)
static void add(blender::Map< std::string, std::string > &messages, Message &msg)
bool contains(const VArray< bool > &varray, const IndexMask &indices_to_check, bool value)
bool remove(void *owner, const StringRef name)
GAttributeReader lookup(const void *owner, const StringRef name)
static PyObject * create_func(PyObject *, PyObject *args)