package com.carrotsearch.hppc;
import java.util.Locale;
import java.util.concurrent.TimeUnit;
import org.junit.Test;
import com.carrotsearch.hppc.cursors.IntCursor;
import com.carrotsearch.randomizedtesting.RandomizedTest;
public class HashCollisionsClusteringTest extends RandomizedTest
{
private static boolean debugging = false;
/** @see "http://issues.carrot2.org/browse/HPPC-80" */
@Test
public void testHashSetClusteringOnRehash()
{
IntHashSet source = new IntHashSet(0, 0.9d);
for (int i = 1250000; i-- != 0;) {
source.add(i);
}
IntHashSet target = new IntHashSet(0, 0.9d);
int i = 0;
long start = System.currentTimeMillis();
long deadline = start + TimeUnit.SECONDS.toMillis(3);
for (IntCursor c : source) {
target.add(c.value);
if ((i++ % 5000) == 0) {
System.out.println(String.format(Locale.ROOT,
"Keys: %7d, %5d ms.",
i,
System.currentTimeMillis() - start));
if (System.currentTimeMillis() >= deadline) {
fail("Takes too long, something is wrong. Added " + i + " keys out of " + source.size());
}
}
}
}
/** @see "http://issues.carrot2.org/browse/HPPC-80" */
@Test
public void testHashMapClusteringOnRehash()
{
IntIntHashMap a = new IntIntHashMap();
for (int i = 10000000; i-- != 0;) {
a.put(i, 0);
}
IntIntHashMap b2 = new IntIntHashMap();
b2.putAll(a);
}
/** */
@Test
public void testHashSetClusteringAtFront()
{
int keys = 500000;
IntHashSet target = new IntHashSet(keys, 0.9) {
@Override
protected void allocateBuffers(int arraySize) {
super.allocateBuffers(arraySize);
System.out.println("Rehashed to: " + arraySize);
}
};
int expandAtCount = HashContainers.expandAtCount(target.keys.length - 1, 0.9);
int fillUntil = expandAtCount - 100000;
IntHashSet source = new IntHashSet(keys, 0.9);
int unique = 0;
while (source.size() < expandAtCount - 1) {
source.add(unique++);
}
System.out.println("Source filled up.");
while (target.size() < fillUntil) {
target.add(unique++);
}
System.out.println("Target filled up.");
assertEquals(source.keys.length, target.keys.length);
long start = System.currentTimeMillis();
long deadline = start + TimeUnit.SECONDS.toMillis(5);
int i = 0;
for (IntCursor c : source) {
target.add(c.value);
if ((i++ % 5000) == 0) {
if (source.keys.length == target.keys.length) {
System.out.println(String.format(Locale.ROOT,
"Keys: %7d, %5d ms.: %s",
i,
System.currentTimeMillis() - start,
debugging ? target.visualizeKeyDistribution(80) : "--"));
}
if (System.currentTimeMillis() >= deadline) {
fail("Takes too long, something is wrong. Added " + i + " keys out of " + source.size());
}
}
}
}
/** */
@Test
public void testHashSetClusteringAtFront2()
{
int keys = 100000;
int expected = keys * 5;
IntHashSet target = new IntHashSet(expected, 0.9) {
@Override
protected void allocateBuffers(int arraySize) {
super.allocateBuffers(arraySize);
System.out.println("[Rehashed to: " + arraySize + "]");
}
};
long deadline = System.currentTimeMillis() + TimeUnit.SECONDS.toMillis(15);
IntHashSet source = new IntHashSet(expected, 0.9);
int unique = 0;
for (int i = 0; i < 200; i++) {
source.clear();
while (source.size() < keys) {
source.add(unique++);
}
long s = System.currentTimeMillis();
int firstSubsetOfKeys = 5000;
for (IntCursor c : source) {
target.add(c.value);
if (firstSubsetOfKeys-- == 0) break;
}
long e = System.currentTimeMillis();
System.out.println(String.format(Locale.ROOT,
"Keys: %7d, %5d ms. (%5d): %s",
i,
e - s,
deadline - e,
debugging ? target.visualizeKeyDistribution(80) : "--"));
if (System.currentTimeMillis() > deadline) {
fail("Takes too long, something is wrong. Added " + i + " batches.");
}
}
}
}