start small and expand to large
1 import std.algorithm.comparison : equal; 2 import nxt.digestx.fnv : FNV; 3 import nxt.array_help : s; 4 5 // construct small 6 alias X = SSOOpenHashSet!(K, FNV!(64, true)); 7 static assert(X.sizeof == 24); 8 auto x = X.withCapacity(X.small.maxCapacity); 9 assert(x.isSmall); 10 assert(x.capacity == X.small.maxCapacity); 11 assert(x.length == 0); 12 13 auto k42 = new K(42); 14 auto k43 = new K(43); 15 auto k44 = new K(44); 16 17 // insert first into small 18 19 assert(!x.contains(k42)); 20 21 assert(x.insert(k42) == x.InsertionStatus.added); 22 assert(x.contains(k42)); 23 24 assert(x.remove(k42)); 25 assert(!x.contains(k42)); 26 27 assert(x.insert(k42) == x.InsertionStatus.added); 28 assert(x.contains(k42)); 29 30 assert(x.byElement.equal!((a, b) => a is b)([k42].s[])); 31 assert(x.isSmall); 32 assert(x.length == 1); 33 34 // insert second into small 35 36 assert(!x.contains(k43)); 37 38 assert(x.insert(k43) == x.InsertionStatus.added); 39 assert(x.contains(k42)); 40 assert(x.contains(k43)); 41 42 assert(x.remove(k43)); 43 assert(x.remove(k42)); 44 assert(!x.contains(k43)); 45 assert(!x.contains(k42)); 46 47 assert(x.insert(k43) == x.InsertionStatus.added); 48 assert(x.insert(k42) == x.InsertionStatus.added); 49 50 assert(x.byElement.equal!((a, b) => a is b)([k43, k42].s[])); 51 assert(x.isSmall); 52 assert(x.length == 2); 53 54 // expanding insert third into large 55 56 assert(!x.contains(k44)); 57 assert(x.insert(k44) == x.InsertionStatus.added); 58 // unordered store so equal doesn't work anymore 59 assert(x.contains(k42)); 60 assert(x.contains(k43)); 61 assert(x.contains(k44)); 62 foreach (ref e; x.byElement) 63 { 64 static assert(is(typeof(e) == K)); 65 assert(x.contains(e)); 66 } 67 assert(x.isLarge); 68 assert(x.length == 3); 69 70 // shrinking remove third into small 71 assert(x.remove(k44)); 72 assert(!x.contains(k44)); 73 assert(x.isSmall); 74 assert(x.length == 2); 75 assert(x.byElement.equal!((a, b) => a is b)([k43, k42].s[])); 76 // auto xr = x.byElement; 77 // assert(xr.front.value == 43); 78 // assert(xr.front is k43); 79 // xr.popFront(); 80 // assert(xr.front.value == 42); 81 // assert(xr.front is k42); 82 // xr.popFront(); 83 // assert(xr.empty); 84 85 const cx = X.withCapacity(X.small.maxCapacity); 86 foreach (ref e; cx.byElement) 87 { 88 static assert(is(typeof(e) == K)); // head-const because of `is`-equality 89 }
start large
import nxt.digestx.fnv : FNV; alias X = SSOOpenHashSet!(K, FNV!(64, true)); import nxt.container_traits : mustAddGCRange; static assert(mustAddGCRange!K); static assert(mustAddGCRange!X); auto x = X.withCapacity(3); assert(x.isLarge); assert(x.capacity == 4); // nextPow2(3) assert(x.length == 0); assert(x.insert(new K(42)) == x.InsertionStatus.added); assert(x.length == 1); assert(x.insert(new K(43)) == x.InsertionStatus.added); assert(x.length == 2);