package com.ldbc.driver.generator; import com.google.common.collect.Iterators; import com.ldbc.driver.util.Histogram; import com.ldbc.driver.util.NumberHelper; import org.junit.Before; import org.junit.Test; import java.util.ArrayList; import java.util.Iterator; import java.util.List; import static java.lang.String.format; import static org.hamcrest.CoreMatchers.is; import static org.junit.Assert.assertThat; public abstract class GeneratorTest<GENERATE_TYPE, COUNT extends Number> { private final long RANDOM_SEED = 42; private final int SAMPLE_SIZE = 1000000; private GeneratorFactory generatorFactory = null; public abstract Histogram<GENERATE_TYPE,COUNT> getExpectedDistribution(); public abstract double getDistributionTolerance(); public abstract Iterator<GENERATE_TYPE> getGeneratorImpl( GeneratorFactory generatorFactory ); protected final int getSampleSize() { return SAMPLE_SIZE; } protected final GeneratorFactory getGeneratorFactory() { return generatorFactory; } @Before public final void initGeneratorFactory() { generatorFactory = new GeneratorFactory( new RandomDataGeneratorFactory( RANDOM_SEED ) ); } @Test public final void determinismTest() { GeneratorFactory generatorFactoryA = new GeneratorFactory( new RandomDataGeneratorFactory( RANDOM_SEED ) ); GeneratorFactory generatorFactoryB = new GeneratorFactory( new RandomDataGeneratorFactory( RANDOM_SEED ) ); Iterator<GENERATE_TYPE> sequenceA = Iterators.limit( getGeneratorImpl( generatorFactoryA ), getSampleSize() ); Iterator<GENERATE_TYPE> sequenceB = Iterators.limit( getGeneratorImpl( generatorFactoryB ), getSampleSize() ); assertThat( Iterators.elementsEqual( sequenceA, sequenceB ), is( true ) ); } @Test public final void distributionTest() { // Given GeneratorFactory generatorFactory = new GeneratorFactory( new RandomDataGeneratorFactory( RANDOM_SEED ) ); Iterator<GENERATE_TYPE> generator = getGeneratorImpl( generatorFactory ); Histogram<GENERATE_TYPE,COUNT> expectedDistribution = getExpectedDistribution(); // When List<GENERATE_TYPE> generatedSequence = generateSequence( generator, getSampleSize() ); // getExpectedDistribution() ensures same histogram dimensions/types Histogram<GENERATE_TYPE,COUNT> generatedDistribution = getExpectedDistribution(); NumberHelper<COUNT> number = NumberHelper.createNumberHelper( generatedDistribution.getDefaultBucketValue().getClass() ); generatedDistribution.setAllBucketValues( number.zero() ); generatedDistribution.importValueSequence( generatedSequence ); // Then Histogram<GENERATE_TYPE,Double> expectedDistributionAsPercentage = expectedDistribution.toPercentageValues(); Histogram<GENERATE_TYPE,Double> generatedDistributionAsPercentage = generatedDistribution.toPercentageValues(); String errMsg = format( "Distributions should be within tolerance[%s]\nExpected[%s]\nGenerated[%s]", getDistributionTolerance(), expectedDistributionAsPercentage, generatedDistributionAsPercentage ); assertThat( errMsg, Histogram.equalsWithinTolerance( generatedDistributionAsPercentage, expectedDistributionAsPercentage, getDistributionTolerance() ), is( true ) ); } public final List<GENERATE_TYPE> generateSequence( Iterator<GENERATE_TYPE> generator, Integer size ) { List<GENERATE_TYPE> generatedNumberSequence = new ArrayList<GENERATE_TYPE>(); for ( int i = 0; i < size; i++ ) { GENERATE_TYPE next = generator.next(); generatedNumberSequence.add( next ); } return generatedNumberSequence; } }