/** ************************ TEST MUTATION ******************************************* */ @Test public void testOversizedMiddleInsert() { TreeSet<Integer> canon = new TreeSet<>(); for (int i = 0; i < 10000000; i++) canon.add(i); Object[] btree = BTree.build(Arrays.asList(Integer.MIN_VALUE, Integer.MAX_VALUE), UpdateFunction.noOp()); btree = BTree.update(btree, naturalOrder(), canon, UpdateFunction.<Integer>noOp()); canon.add(Integer.MIN_VALUE); canon.add(Integer.MAX_VALUE); assertTrue(BTree.isWellFormed(btree, naturalOrder())); testEqual("Oversize", BTree.iterator(btree), canon.iterator()); }
@Test public void testSlicingAllSmallTrees() throws ExecutionException, InterruptedException { Object[] cur = BTree.empty(); TreeSet<Integer> canon = new TreeSet<>(); // we set FAN_FACTOR to 4, so 128 items is four levels deep, three fully populated for (int i = 0; i < 128; i++) { String id = String.format("[0..%d)", canon.size()); log("Testing " + id); Futures.allAsList(testAllSlices(id, cur, canon)).get(); Object[] next = null; while (next == null) next = BTree.update(cur, naturalOrder(), Arrays.asList(i), SPORADIC_ABORT); cur = next; canon.add(i); } }
private static RandomTree randomTreeByBuilder(int minSize, int maxSize) { assert minSize > 3; ThreadLocalRandom random = ThreadLocalRandom.current(); BTree.Builder<Integer> builder = BTree.builder(naturalOrder()); int targetSize = random.nextInt(minSize, maxSize); int maxModificationSize = (int) Math.sqrt(targetSize); TreeSet<Integer> canonical = new TreeSet<>(); int curSize = 0; TreeSet<Integer> ordered = new TreeSet<>(); List<Integer> shuffled = new ArrayList<>(); while (curSize < targetSize) { int nextSize = maxModificationSize <= 1 ? 1 : random.nextInt(1, maxModificationSize); // leave a random selection of previous values (random.nextBoolean() ? ordered.headSet(random.nextInt()) : ordered.tailSet(random.nextInt())) .clear(); shuffled = new ArrayList<>( shuffled.subList(0, shuffled.size() < 2 ? 0 : random.nextInt(shuffled.size() / 2))); for (int i = 0; i < nextSize; i++) { Integer next = random.nextInt(); ordered.add(next); shuffled.add(next); canonical.add(next); } switch (random.nextInt(5)) { case 0: builder.addAll(ordered); break; case 1: builder.addAll(BTreeSet.of(ordered)); break; case 2: for (Integer i : ordered) builder.add(i); case 3: builder.addAll(shuffled); break; case 4: for (Integer i : shuffled) builder.add(i); } curSize += nextSize; maxModificationSize = Math.min(maxModificationSize, targetSize - curSize); } BTreeSet<Integer> btree = BTreeSet.<Integer>wrap(builder.build(), naturalOrder()); Assert.assertEquals(canonical.size(), btree.size()); return new RandomTree(canonical, btree); }
BTreeRange( Object[] tree, Comparator<? super V> comparator, V lowerBound, boolean inclusiveLowerBound, V upperBound, boolean inclusiveUpperBound) { this( tree, comparator, lowerBound == null ? 0 : inclusiveLowerBound ? BTree.ceilIndex(tree, comparator, lowerBound) : BTree.higherIndex(tree, comparator, lowerBound), upperBound == null ? BTree.size(tree) - 1 : inclusiveUpperBound ? BTree.floorIndex(tree, comparator, upperBound) : BTree.lowerIndex(tree, comparator, upperBound)); }
private static RandomTree randomTreeByUpdate(int minSize, int maxSize) { assert minSize > 3; TreeSet<Integer> canonical = new TreeSet<>(); ThreadLocalRandom random = ThreadLocalRandom.current(); int targetSize = random.nextInt(minSize, maxSize); int maxModificationSize = random.nextInt(2, targetSize); Object[] accmumulate = BTree.empty(); int curSize = 0; while (curSize < targetSize) { int nextSize = maxModificationSize == 1 ? 1 : random.nextInt(1, maxModificationSize); TreeSet<Integer> build = new TreeSet<>(); for (int i = 0; i < nextSize; i++) { Integer next = random.nextInt(); build.add(next); canonical.add(next); } accmumulate = BTree.update(accmumulate, naturalOrder(), build, UpdateFunction.<Integer>noOp()); curSize += nextSize; maxModificationSize = Math.min(maxModificationSize, targetSize - curSize); } return new RandomTree(canonical, BTreeSet.<Integer>wrap(accmumulate, naturalOrder())); }
@Test public void testTransformAndFilter() throws InterruptedException { testRandomSelection( perThreadTrees, 4, false, false, false, (selection) -> { Map<Integer, Integer> update = new LinkedHashMap<>(); for (Integer i : selection.testKeys) update.put(i, new Integer(i)); CountingFunction function; Object[] original = selection.testAsSet.tree(); Object[] transformed; // test replacing none, leaving all present function = new CountingFunction((x) -> x); transformed = BTree.transformAndFilter(original, function); Assert.assertEquals(BTree.size(original), function.count); Assert.assertSame(original, transformed); // test replacing some, leaving all present function = new CountingFunction((x) -> update.containsKey(x) ? update.get(x) : x); transformed = BTree.transformAndFilter(original, function); Assert.assertEquals(BTree.size(original), function.count); assertSame(transform(selection.canonicalList, function.wrapped), iterable(transformed)); // test replacing some, removing some function = new CountingFunction(update::get); transformed = BTree.transformAndFilter(original, function); Assert.assertEquals(BTree.size(original), function.count); assertSame( filter(transform(selection.canonicalList, function.wrapped), notNull()), iterable(transformed)); // test replacing none, removing some function = new CountingFunction((x) -> update.containsKey(x) ? null : x); transformed = BTree.transformAndFilter(selection.testAsList.tree(), function); Assert.assertEquals(BTree.size(original), function.count); assertSame( filter(transform(selection.canonicalList, function.wrapped), notNull()), iterable(transformed)); }); }
public static <V> BTreeSet<V> of(Comparator<? super V> comparator, V value) { return new BTreeSet<>( BTree.build(ImmutableList.of(value), UpdateFunction.<V>noOp()), comparator); }
public static <V> BTreeSet<V> empty(Comparator<? super V> comparator) { return new BTreeSet<>(BTree.empty(), comparator); }
public static <V extends Comparable<V>> BTreeSet<V> of(V value) { return new BTreeSet<>( BTree.build(ImmutableList.of(value), UpdateFunction.<V>noOp()), Ordering.<V>natural()); }
public static <V extends Comparable<V>> BTreeSet<V> of(Collection<V> sortedValues) { return new BTreeSet<>( BTree.build(sortedValues, UpdateFunction.<V>noOp()), Ordering.<V>natural()); }
@Override public V higher(V v) { return BTree.higher(tree, comparator, v); }
@Override public boolean isEmpty() { return BTree.isEmpty(tree); }
public <T> T[] toArray(T[] a, int offset) { if (size() + offset < a.length) a = Arrays.copyOf(a, size() + offset); BTree.toArray(tree, lowerBound, upperBound + 1, a, offset); return a; }
public BTreeSet<V> update(Collection<V> updateWith) { return new BTreeSet<>( BTree.update(tree, comparator, updateWith, UpdateFunction.<V>noOp()), comparator); }
public V higher(V v) { return maybe(Math.max(lowerBound, BTree.higherIndex(tree, comparator, v))); }
public V ceiling(V v) { return maybe(Math.max(lowerBound, BTree.ceilIndex(tree, comparator, v))); }
public V floor(V v) { return maybe(Math.min(upperBound, BTree.floorIndex(tree, comparator, v))); }
/** * The converse of indexOf: provided an index between 0 and size, returns the i'th item, in set * order. */ public V get(int index) { return BTree.<V>findByIndex(tree, index); }
@Override public int size() { return BTree.size(tree); }
public V get(int index) { index = upperBound - index; if (outOfBounds(index)) throw new NoSuchElementException(); return BTree.findByIndex(tree, index); }
@Override public V floor(V v) { return BTree.floor(tree, comparator, v); }
@Override public V lower(V v) { return BTree.lower(tree, comparator, v); }
protected BTreeSearchIterator<V, V> slice(Dir dir) { return BTree.slice(tree, comparator, dir); }
@Override public V ceiling(V v) { return BTree.ceil(tree, comparator, v); }
protected Builder(Comparator<? super V> comparator) { builder = BTree.builder(comparator); }
public <T> T[] toArray(T[] a, int offset) { int size = size(); if (a.length < size + offset) a = Arrays.copyOf(a, size); BTree.toArray(tree, a, offset); return a; }