diff --git a/test/yulPhaser/Common.cpp b/test/yulPhaser/Common.cpp index 93aa432fa..52cde9590 100644 --- a/test/yulPhaser/Common.cpp +++ b/test/yulPhaser/Common.cpp @@ -24,6 +24,12 @@ using namespace std; using namespace solidity; using namespace solidity::yul; +using namespace solidity::phaser; + +function phaser::test::wholeChromosomeReplacement(Chromosome _newChromosome) +{ + return [_newChromosome = move(_newChromosome)](Chromosome const&) { return _newChromosome; }; +} vector phaser::test::chromosomeLengths(Population const& _population) { @@ -44,6 +50,15 @@ map phaser::test::enumerateOptmisationSteps() return stepIndices; } +size_t phaser::test::countDifferences(Chromosome const& _chromosome1, Chromosome const& _chromosome2) +{ + size_t count = 0; + for (size_t i = 0; i < min(_chromosome1.length(), _chromosome2.length()); ++i) + count += static_cast(_chromosome1.optimisationSteps()[i] != _chromosome2.optimisationSteps()[i]); + + return count + abs(static_cast(_chromosome1.length() - _chromosome2.length())); +} + string phaser::test::stripWhitespace(string const& input) { regex whitespaceRegex("\\s+"); diff --git a/test/yulPhaser/Common.h b/test/yulPhaser/Common.h index e73260d7a..cbec90f78 100644 --- a/test/yulPhaser/Common.h +++ b/test/yulPhaser/Common.h @@ -30,9 +30,11 @@ #include #include +#include #include #include +#include #include #include #include @@ -52,11 +54,21 @@ public: size_t evaluate(Chromosome const& _chromosome) const override { return _chromosome.length(); } }; +// MUTATIONS + +/// Mutation that always replaces the whole chromosome with the one specified in the parameter. +std::function wholeChromosomeReplacement(Chromosome _newChromosome); + // CHROMOSOME AND POPULATION HELPERS /// Returns a vector containing lengths of all chromosomes in the population (in the same order). std::vector chromosomeLengths(Population const& _population); +/// Returns the number of genes that differ between two chromosomes. +/// If the chromnosomes have different lengths, the positions that are present in only one of them +/// are counted as mismatches. +size_t countDifferences(Chromosome const& _chromosome1, Chromosome const& _chromosome2); + /// Assigns indices from 0 to N to all optimisation steps available in the OptimiserSuite. /// This is a convenience helper to make it easier to test their distribution with tools made for /// integers. diff --git a/test/yulPhaser/CommonTest.cpp b/test/yulPhaser/CommonTest.cpp index 9bcab9923..3456a6640 100644 --- a/test/yulPhaser/CommonTest.cpp +++ b/test/yulPhaser/CommonTest.cpp @@ -40,6 +40,12 @@ BOOST_AUTO_TEST_CASE(ChromosomeLengthMetric_evaluate_should_return_chromosome_le BOOST_TEST(ChromosomeLengthMetric{}.evaluate(Chromosome("aaaaa")) == 5); } +BOOST_AUTO_TEST_CASE(wholeChromosomeReplacement_should_replace_whole_chromosome_with_another) +{ + function mutation = wholeChromosomeReplacement(Chromosome("aaa")); + BOOST_TEST(mutation(Chromosome("ccc")) == Chromosome("aaa")); +} + BOOST_AUTO_TEST_CASE(chromosomeLengths_should_return_lengths_of_all_chromosomes_in_a_population) { shared_ptr fitnessMetric = make_shared(); @@ -51,6 +57,34 @@ BOOST_AUTO_TEST_CASE(chromosomeLengths_should_return_lengths_of_all_chromosomes_ BOOST_TEST((chromosomeLengths(population2) == vector{})); } +BOOST_AUTO_TEST_CASE(countDifferences_should_return_zero_for_identical_chromosomes) +{ + BOOST_TEST(countDifferences(Chromosome(), Chromosome()) == 0); + BOOST_TEST(countDifferences(Chromosome("a"), Chromosome("a")) == 0); + BOOST_TEST(countDifferences(Chromosome("afxT"), Chromosome("afxT")) == 0); +} + +BOOST_AUTO_TEST_CASE(countDifferences_should_count_mismatched_positions_in_chromosomes_of_the_same_length) +{ + BOOST_TEST(countDifferences(Chromosome("a"), Chromosome("f")) == 1); + BOOST_TEST(countDifferences(Chromosome("aa"), Chromosome("ac")) == 1); + BOOST_TEST(countDifferences(Chromosome("ac"), Chromosome("cc")) == 1); + BOOST_TEST(countDifferences(Chromosome("aa"), Chromosome("cc")) == 2); + BOOST_TEST(countDifferences(Chromosome("afxT"), Chromosome("Txfa")) == 4); +} + +BOOST_AUTO_TEST_CASE(countDifferences_should_count_missing_characters_as_differences) +{ + BOOST_TEST(countDifferences(Chromosome(""), Chromosome("a")) == 1); + BOOST_TEST(countDifferences(Chromosome("a"), Chromosome("")) == 1); + BOOST_TEST(countDifferences(Chromosome("aa"), Chromosome("")) == 2); + BOOST_TEST(countDifferences(Chromosome("aaa"), Chromosome("")) == 3); + + BOOST_TEST(countDifferences(Chromosome("aa"), Chromosome("aaaa")) == 2); + BOOST_TEST(countDifferences(Chromosome("aa"), Chromosome("aacc")) == 2); + BOOST_TEST(countDifferences(Chromosome("aa"), Chromosome("cccc")) == 4); +} + BOOST_AUTO_TEST_CASE(enumerateOptimisationSteps_should_assing_indices_to_all_available_optimisation_steps) { map stepsAndAbbreviations = OptimiserSuite::stepNameToAbbreviationMap();