|
@@ -2,10 +2,33 @@
|
|
|
#include "../Tests.hpp"
|
|
|
#include "core/data/ProbingHashMap.hpp"
|
|
|
#include "core/utils/Error.hpp"
|
|
|
+#include "core/utils/HashCode.hpp"
|
|
|
|
|
|
template struct Core::ProbingHashMap<int, int>;
|
|
|
using IntMap = Core::ProbingHashMap<int, int>;
|
|
|
|
|
|
+constexpr int INVALID = Core::emptyValue<int>();
|
|
|
+
|
|
|
+static IntMap getTestIntMap() {
|
|
|
+ IntMap map;
|
|
|
+ map.add(1, 3).add(2, 4).add(3, 5).add(INVALID, 20);
|
|
|
+ return map;
|
|
|
+}
|
|
|
+
|
|
|
+static void checkIntMap(IntMap& map) {
|
|
|
+ int* a = map.search(1);
|
|
|
+ int* b = map.search(2);
|
|
|
+ int* c = map.search(3);
|
|
|
+ int* d = map.search(INVALID);
|
|
|
+ if(CORE_TEST_NOT_NULL(a) && CORE_TEST_NOT_NULL(b) &&
|
|
|
+ CORE_TEST_NOT_NULL(c) && CORE_TEST_NOT_NULL(d)) {
|
|
|
+ CORE_TEST_EQUAL(3, *a);
|
|
|
+ CORE_TEST_EQUAL(4, *b);
|
|
|
+ CORE_TEST_EQUAL(5, *c);
|
|
|
+ CORE_TEST_EQUAL(20, *d);
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
static void testAdd() {
|
|
|
IntMap map;
|
|
|
map.add(5, 4);
|
|
@@ -17,22 +40,11 @@ static void testAdd() {
|
|
|
}
|
|
|
|
|
|
static void testMultipleAdd() {
|
|
|
- IntMap map;
|
|
|
- map.add(5, 4).add(10, 3).add(15, 2);
|
|
|
- CORE_TEST_TRUE(map.contains(5));
|
|
|
- CORE_TEST_TRUE(map.contains(10));
|
|
|
- CORE_TEST_TRUE(map.contains(15));
|
|
|
- int* a = map.search(5);
|
|
|
- int* b = map.search(10);
|
|
|
- int* c = map.search(15);
|
|
|
- CORE_TEST_NOT_NULL(a);
|
|
|
- CORE_TEST_NOT_NULL(b);
|
|
|
- CORE_TEST_NOT_NULL(c);
|
|
|
- if(a != nullptr && b != nullptr && c != nullptr) {
|
|
|
- CORE_TEST_EQUAL(4, *a);
|
|
|
- CORE_TEST_EQUAL(3, *b);
|
|
|
- CORE_TEST_EQUAL(2, *c);
|
|
|
- }
|
|
|
+ IntMap map = getTestIntMap();
|
|
|
+ CORE_TEST_TRUE(map.contains(1));
|
|
|
+ CORE_TEST_TRUE(map.contains(2));
|
|
|
+ CORE_TEST_TRUE(map.contains(3));
|
|
|
+ checkIntMap(map);
|
|
|
}
|
|
|
|
|
|
static void testSearch() {
|
|
@@ -47,8 +59,7 @@ static void testAddReplace() {
|
|
|
map.add(5, 4).add(5, 10);
|
|
|
CORE_TEST_TRUE(map.contains(5));
|
|
|
int* a = map.search(5);
|
|
|
- CORE_TEST_NOT_NULL(a);
|
|
|
- if(a != nullptr) {
|
|
|
+ if(CORE_TEST_NOT_NULL(a)) {
|
|
|
CORE_TEST_EQUAL(10, *a);
|
|
|
}
|
|
|
}
|
|
@@ -64,42 +75,42 @@ static void testClear() {
|
|
|
static void testOverflow(bool light) {
|
|
|
int limit = light ? 10000 : 100000;
|
|
|
IntMap map;
|
|
|
+ map.add(INVALID, 42);
|
|
|
for(int i = 0; i < limit; i++) {
|
|
|
map.add(i, i);
|
|
|
}
|
|
|
for(int i = 0; i < limit; i++) {
|
|
|
CORE_TEST_TRUE(map.contains(i));
|
|
|
}
|
|
|
+ CORE_TEST_TRUE(map.contains(INVALID));
|
|
|
}
|
|
|
|
|
|
static int aInstances = 0;
|
|
|
|
|
|
-struct ProbingHashMapTestStruct final {
|
|
|
+struct ProbingTest final {
|
|
|
int a;
|
|
|
int b;
|
|
|
|
|
|
- ProbingHashMapTestStruct(int a_, int b_) : a(a_), b(b_) {
|
|
|
+ ProbingTest(int a_, int b_) : a(a_), b(b_) {
|
|
|
aInstances++;
|
|
|
}
|
|
|
|
|
|
- ProbingHashMapTestStruct(const ProbingHashMapTestStruct& o)
|
|
|
- : a(o.a), b(o.b) {
|
|
|
+ ProbingTest(const ProbingTest& o) : a(o.a), b(o.b) {
|
|
|
aInstances++;
|
|
|
}
|
|
|
|
|
|
- ProbingHashMapTestStruct(ProbingHashMapTestStruct&& o) : a(o.a), b(o.b) {
|
|
|
+ ProbingTest(ProbingTest&& o) : a(o.a), b(o.b) {
|
|
|
aInstances++;
|
|
|
}
|
|
|
|
|
|
- ~ProbingHashMapTestStruct() {
|
|
|
+ ~ProbingTest() {
|
|
|
aInstances--;
|
|
|
}
|
|
|
|
|
|
- ProbingHashMapTestStruct&
|
|
|
- operator=(const ProbingHashMapTestStruct& o) = default;
|
|
|
- ProbingHashMapTestStruct& operator=(ProbingHashMapTestStruct&& o) = default;
|
|
|
+ ProbingTest& operator=(const ProbingTest& o) = default;
|
|
|
+ ProbingTest& operator=(ProbingTest&& o) = default;
|
|
|
|
|
|
- bool operator==(const ProbingHashMapTestStruct& other) const {
|
|
|
+ bool operator==(const ProbingTest& other) const {
|
|
|
return a == other.a && b == other.b;
|
|
|
}
|
|
|
|
|
@@ -116,105 +127,56 @@ struct ProbingHashMapTestStruct final {
|
|
|
|
|
|
static void testEmplace() {
|
|
|
{
|
|
|
- Core::ProbingHashMap<int, ProbingHashMapTestStruct> map;
|
|
|
+ Core::ProbingHashMap<int, ProbingTest> map;
|
|
|
|
|
|
- ProbingHashMapTestStruct* ar = nullptr;
|
|
|
+ ProbingTest* ar = nullptr;
|
|
|
CORE_TEST_TRUE(map.tryEmplace(ar, 0, 3, 4));
|
|
|
CORE_TEST_TRUE(map.tryEmplace(ar, 3, 4, 5));
|
|
|
CORE_TEST_TRUE(map.tryEmplace(ar, 20, 5, 6));
|
|
|
CORE_TEST_FALSE(map.tryEmplace(ar, 3, 6, 7));
|
|
|
CORE_TEST_FALSE(map.tryEmplace(ar, 20, 7, 8));
|
|
|
|
|
|
- ProbingHashMapTestStruct* a = map.search(0);
|
|
|
- ProbingHashMapTestStruct* b = map.search(3);
|
|
|
- ProbingHashMapTestStruct* c = map.search(20);
|
|
|
+ ProbingTest* a = map.search(0);
|
|
|
+ ProbingTest* b = map.search(3);
|
|
|
+ ProbingTest* c = map.search(20);
|
|
|
|
|
|
- CORE_TEST_NOT_NULL(a);
|
|
|
- CORE_TEST_NOT_NULL(b);
|
|
|
- CORE_TEST_NOT_NULL(c);
|
|
|
-
|
|
|
- if(a != nullptr && b != nullptr && c != nullptr) {
|
|
|
- CORE_TEST_EQUAL(ProbingHashMapTestStruct(3, 4), *a);
|
|
|
- CORE_TEST_EQUAL(ProbingHashMapTestStruct(4, 5), *b);
|
|
|
- CORE_TEST_EQUAL(ProbingHashMapTestStruct(5, 6), *c);
|
|
|
+ if(CORE_TEST_NOT_NULL(a) && CORE_TEST_NOT_NULL(b) &&
|
|
|
+ CORE_TEST_NOT_NULL(c)) {
|
|
|
+ CORE_TEST_EQUAL(ProbingTest(3, 4), *a);
|
|
|
+ CORE_TEST_EQUAL(ProbingTest(4, 5), *b);
|
|
|
+ CORE_TEST_EQUAL(ProbingTest(5, 6), *c);
|
|
|
}
|
|
|
}
|
|
|
CORE_TEST_EQUAL(0, aInstances);
|
|
|
}
|
|
|
|
|
|
-static void testToString1() {
|
|
|
- IntMap map;
|
|
|
- map.add(1, 3).add(2, 4).add(3, 5);
|
|
|
- CORE_TEST_STRING("[2 = 4, 1 = 3, 3 = 5]", map);
|
|
|
-}
|
|
|
-
|
|
|
-static void testToString2() {
|
|
|
- IntMap map;
|
|
|
- map.add(1, 3);
|
|
|
- CORE_TEST_STRING("[1 = 3]", map);
|
|
|
-}
|
|
|
-
|
|
|
-static void testToString3() {
|
|
|
- IntMap map;
|
|
|
- CORE_TEST_STRING("[]", map);
|
|
|
+static void testToString() {
|
|
|
+ CORE_TEST_STRING("[2 = 4, 1 = 3, 3 = 5, 2147483647 = 20]", getTestIntMap());
|
|
|
+ CORE_TEST_STRING("[1 = 3]", IntMap().add(1, 3));
|
|
|
+ CORE_TEST_STRING("[]", IntMap());
|
|
|
}
|
|
|
|
|
|
static void testCopy() {
|
|
|
- IntMap map;
|
|
|
- map.add(1, 3).add(2, 4).add(3, 5);
|
|
|
+ IntMap map = getTestIntMap();
|
|
|
IntMap copy = map;
|
|
|
-
|
|
|
- int* a[6] = {map.search(1), map.search(2), map.search(3),
|
|
|
- copy.search(1), copy.search(2), copy.search(3)};
|
|
|
- for(int i = 0; i < 3; i++) {
|
|
|
- CORE_TEST_NOT_NULL(a[i]);
|
|
|
- CORE_TEST_NOT_NULL(a[i + 3]);
|
|
|
- if(a[i] != nullptr && a[i + 3] != nullptr) {
|
|
|
- CORE_TEST_EQUAL(*(a[i]), *(a[i + 3]));
|
|
|
- }
|
|
|
- }
|
|
|
+ IntMap copyA;
|
|
|
+ copyA = map;
|
|
|
+ checkIntMap(map);
|
|
|
+ checkIntMap(copy);
|
|
|
+ checkIntMap(copyA);
|
|
|
}
|
|
|
|
|
|
static void testMove() {
|
|
|
- IntMap map;
|
|
|
- map.add(1, 3).add(2, 4).add(3, 5);
|
|
|
+ IntMap map = getTestIntMap();
|
|
|
IntMap move(Core::move(map));
|
|
|
-
|
|
|
- int* a = move.search(1);
|
|
|
- int* b = move.search(2);
|
|
|
- int* c = move.search(3);
|
|
|
-
|
|
|
- CORE_TEST_NOT_NULL(a);
|
|
|
- CORE_TEST_NOT_NULL(b);
|
|
|
- CORE_TEST_NOT_NULL(c);
|
|
|
-
|
|
|
- if(a != nullptr && b != nullptr && c != nullptr) {
|
|
|
- CORE_TEST_EQUAL(3, *a);
|
|
|
- CORE_TEST_EQUAL(4, *b);
|
|
|
- CORE_TEST_EQUAL(5, *c);
|
|
|
- }
|
|
|
+ checkIntMap(move);
|
|
|
}
|
|
|
|
|
|
static void testMoveAssignment() {
|
|
|
- IntMap map;
|
|
|
- map.add(1, 3).add(2, 4).add(3, 5);
|
|
|
-
|
|
|
+ IntMap map = getTestIntMap();
|
|
|
IntMap move;
|
|
|
move = Core::move(map);
|
|
|
-
|
|
|
- int* a = move.search(1);
|
|
|
- int* b = move.search(2);
|
|
|
- int* c = move.search(3);
|
|
|
-
|
|
|
- CORE_TEST_NOT_NULL(a);
|
|
|
- CORE_TEST_NOT_NULL(b);
|
|
|
- CORE_TEST_NOT_NULL(c);
|
|
|
-
|
|
|
- if(a != nullptr && b != nullptr && c != nullptr) {
|
|
|
- CORE_TEST_EQUAL(3, *a);
|
|
|
- CORE_TEST_EQUAL(4, *b);
|
|
|
- CORE_TEST_EQUAL(5, *c);
|
|
|
- }
|
|
|
+ checkIntMap(move);
|
|
|
}
|
|
|
|
|
|
static void testEntryForEach() {
|
|
@@ -291,11 +253,33 @@ static void testTypes() {
|
|
|
testType<unsigned long long>();
|
|
|
}
|
|
|
|
|
|
-static void testInsertInvalid() {
|
|
|
+static void testInvalid() {
|
|
|
IntMap map;
|
|
|
int* v;
|
|
|
- CORE_TEST_TRUE(map.tryEmplace(v, Core::emptyValue<int>(), 2));
|
|
|
- CORE_TEST_EQUAL(3, map.put(Core::emptyValue<int>(), 3));
|
|
|
+ CORE_TEST_TRUE(map.tryEmplace(v, INVALID, 2));
|
|
|
+ if(CORE_TEST_NOT_NULL(v)) {
|
|
|
+ CORE_TEST_EQUAL(2, *v);
|
|
|
+ }
|
|
|
+ CORE_TEST_FALSE(map.tryEmplace(v, INVALID, 6));
|
|
|
+ if(CORE_TEST_NOT_NULL(v)) {
|
|
|
+ CORE_TEST_EQUAL(2, *v);
|
|
|
+ }
|
|
|
+ CORE_TEST_EQUAL(3, map.put(INVALID, 3));
|
|
|
+ v = map.search(INVALID);
|
|
|
+ if(CORE_TEST_NOT_NULL(v)) {
|
|
|
+ CORE_TEST_EQUAL(3, *v);
|
|
|
+ }
|
|
|
+ map.clear();
|
|
|
+ CORE_TEST_NULL(map.search(INVALID));
|
|
|
+}
|
|
|
+
|
|
|
+static void testInvalidPut() {
|
|
|
+ IntMap map;
|
|
|
+ CORE_TEST_EQUAL(3, map.put(INVALID, 3));
|
|
|
+ int* v = map.search(INVALID);
|
|
|
+ if(CORE_TEST_NOT_NULL(v)) {
|
|
|
+ CORE_TEST_EQUAL(3, *v);
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
static void testAddCollisions() {
|
|
@@ -313,9 +297,7 @@ void Core::testProbingHashMap(bool light) {
|
|
|
testClear();
|
|
|
testOverflow(light);
|
|
|
testEmplace();
|
|
|
- testToString1();
|
|
|
- testToString2();
|
|
|
- testToString3();
|
|
|
+ testToString();
|
|
|
testCopy();
|
|
|
testMove();
|
|
|
testMoveAssignment();
|
|
@@ -323,6 +305,7 @@ void Core::testProbingHashMap(bool light) {
|
|
|
testKeyForEach();
|
|
|
testValueForEach();
|
|
|
testTypes();
|
|
|
- testInsertInvalid();
|
|
|
+ testInvalid();
|
|
|
+ testInvalidPut();
|
|
|
testAddCollisions();
|
|
|
}
|