Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 32 additions & 5 deletions src/catch2/matchers/catch_matchers_range_equals.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
#include <catch2/matchers/catch_matchers_templated.hpp>

#include <functional>
#include <vector>

namespace Catch {
namespace Matchers {
Expand Down Expand Up @@ -74,15 +75,41 @@ namespace Catch {
m_predicate( CATCH_FORWARD( predicate ) ) {}

template <typename RangeLike>
#if defined( CATCH_INTERNAL_CONSTEXPR_MATCHERS_ENABLED )
constexpr
#endif
bool match( RangeLike&& rng ) const {
using std::begin;
using std::end;
return Catch::Detail::is_permutation( begin( m_desired ),
end( m_desired ),
begin( rng ),
end( rng ),
m_predicate );

const auto target_begin = begin( m_desired );
const auto target_end = end( m_desired );
const auto target_size = static_cast<size_t>(
Catch::Detail::sentinel_distance( target_begin,
target_end ) );
std::vector<bool> matched( target_size, false );

size_t matched_count = 0;
for ( auto&& element : rng ) {
if ( matched_count == target_size ) { return false; }

auto target = target_begin;
bool found_match = false;
for ( size_t index = 0; target != target_end;
++target, ++index ) {
if ( !matched[index] &&
m_predicate( element, *target ) ) {
matched[index] = true;
++matched_count;
found_match = true;
break;
}
}

if ( !found_match ) { return false; }
}

return matched_count == target_size;
}

std::string describe() const override {
Expand Down
3 changes: 2 additions & 1 deletion tests/SelfTest/Baselines/compact.sw.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2440,6 +2440,7 @@ MatchersRanges.tests.cpp:<line number>: passed: array_a, !UnorderedRangeEquals(
MatchersRanges.tests.cpp:<line number>: passed: vector_a, !UnorderedRangeEquals( vector_b ) for: { 1, 2, 3 } not unordered elements are { 1, 2, 3, 4 }
MatchersRanges.tests.cpp:<line number>: passed: vector_a, UnorderedRangeEquals( vector_a_plus_1, close_enough ) for: { 1, 10, 20 } unordered elements are { 11, 21, 2 }
MatchersRanges.tests.cpp:<line number>: passed: vector_a, !UnorderedRangeEquals( vector_b, close_enough ) for: { 1, 10, 21 } not unordered elements are { 11, 21, 3 }
MatchersRanges.tests.cpp:<line number>: passed: actual, UnorderedRangeEquals( expected, []( UnorderedRangeActual const& lhs, UnorderedRangeExpected const& rhs ) { return lhs.value == rhs.value; } ) for: { 1, 2, 3, 4 } unordered elements are { 4, 2, 3, 1 }
MatchersRanges.tests.cpp:<line number>: passed: needs_adl1, UnorderedRangeEquals( needs_adl2 ) for: { 1, 2, 3, 4, 5 } unordered elements are { 1, 2, 3, 4, 5 }
MatchersRanges.tests.cpp:<line number>: passed: array_a, UnorderedRangeEquals( { 10, 20, 1 } ) for: { 1, 10, 20 } unordered elements are { 10, 20, 1 }
MatchersRanges.tests.cpp:<line number>: passed: array_a, UnorderedRangeEquals( { 11, 21, 2 }, []( int l, int r ) { return std::abs( l - r ) <= 1; } ) for: { 1, 10, 20 } unordered elements are { 11, 21, 2 }
Expand Down Expand Up @@ -3001,6 +3002,6 @@ InternalBenchmark.tests.cpp:<line number>: passed: q3 == 23. for: 23.0 == 23.0
Misc.tests.cpp:<line number>: passed:
Misc.tests.cpp:<line number>: passed:
test cases: 451 | 331 passed | 96 failed | 6 skipped | 18 failed as expected
assertions: 2416 | 2215 passed | 158 failed | 43 failed as expected
assertions: 2417 | 2216 passed | 158 failed | 43 failed as expected


3 changes: 2 additions & 1 deletion tests/SelfTest/Baselines/compact.sw.multi.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2433,6 +2433,7 @@ MatchersRanges.tests.cpp:<line number>: passed: array_a, !UnorderedRangeEquals(
MatchersRanges.tests.cpp:<line number>: passed: vector_a, !UnorderedRangeEquals( vector_b ) for: { 1, 2, 3 } not unordered elements are { 1, 2, 3, 4 }
MatchersRanges.tests.cpp:<line number>: passed: vector_a, UnorderedRangeEquals( vector_a_plus_1, close_enough ) for: { 1, 10, 20 } unordered elements are { 11, 21, 2 }
MatchersRanges.tests.cpp:<line number>: passed: vector_a, !UnorderedRangeEquals( vector_b, close_enough ) for: { 1, 10, 21 } not unordered elements are { 11, 21, 3 }
MatchersRanges.tests.cpp:<line number>: passed: actual, UnorderedRangeEquals( expected, []( UnorderedRangeActual const& lhs, UnorderedRangeExpected const& rhs ) { return lhs.value == rhs.value; } ) for: { 1, 2, 3, 4 } unordered elements are { 4, 2, 3, 1 }
MatchersRanges.tests.cpp:<line number>: passed: needs_adl1, UnorderedRangeEquals( needs_adl2 ) for: { 1, 2, 3, 4, 5 } unordered elements are { 1, 2, 3, 4, 5 }
MatchersRanges.tests.cpp:<line number>: passed: array_a, UnorderedRangeEquals( { 10, 20, 1 } ) for: { 1, 10, 20 } unordered elements are { 10, 20, 1 }
MatchersRanges.tests.cpp:<line number>: passed: array_a, UnorderedRangeEquals( { 11, 21, 2 }, []( int l, int r ) { return std::abs( l - r ) <= 1; } ) for: { 1, 10, 20 } unordered elements are { 11, 21, 2 }
Expand Down Expand Up @@ -2990,6 +2991,6 @@ InternalBenchmark.tests.cpp:<line number>: passed: q3 == 23. for: 23.0 == 23.0
Misc.tests.cpp:<line number>: passed:
Misc.tests.cpp:<line number>: passed:
test cases: 451 | 331 passed | 96 failed | 6 skipped | 18 failed as expected
assertions: 2416 | 2215 passed | 158 failed | 43 failed as expected
assertions: 2417 | 2216 passed | 158 failed | 43 failed as expected


2 changes: 1 addition & 1 deletion tests/SelfTest/Baselines/console.std.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -1744,5 +1744,5 @@ due to unexpected exception with message:

===============================================================================
test cases: 451 | 349 passed | 76 failed | 7 skipped | 19 failed as expected
assertions: 2394 | 2215 passed | 136 failed | 43 failed as expected
assertions: 2395 | 2216 passed | 136 failed | 43 failed as expected

15 changes: 14 additions & 1 deletion tests/SelfTest/Baselines/console.sw.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -16185,6 +16185,19 @@ MatchersRanges.tests.cpp:<line number>: PASSED:
with expansion:
{ 1, 10, 21 } not unordered elements are { 11, 21, 3 }

-------------------------------------------------------------------------------
Usage of UnorderedRangeEquals range matcher
Custom predicate
Different element types keep predicate argument order
-------------------------------------------------------------------------------
MatchersRanges.tests.cpp:<line number>
...............................................................................

MatchersRanges.tests.cpp:<line number>: PASSED:
CHECK_THAT( actual, UnorderedRangeEquals( expected, []( UnorderedRangeActual const& lhs, UnorderedRangeExpected const& rhs ) { return lhs.value == rhs.value; } ) )
with expansion:
{ 1, 2, 3, 4 } unordered elements are { 4, 2, 3, 1 }

-------------------------------------------------------------------------------
Usage of UnorderedRangeEquals range matcher
Ranges that need ADL begin/end
Expand Down Expand Up @@ -20135,5 +20148,5 @@ Misc.tests.cpp:<line number>: PASSED:

===============================================================================
test cases: 451 | 331 passed | 96 failed | 6 skipped | 18 failed as expected
assertions: 2416 | 2215 passed | 158 failed | 43 failed as expected
assertions: 2417 | 2216 passed | 158 failed | 43 failed as expected

15 changes: 14 additions & 1 deletion tests/SelfTest/Baselines/console.sw.multi.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -16178,6 +16178,19 @@ MatchersRanges.tests.cpp:<line number>: PASSED:
with expansion:
{ 1, 10, 21 } not unordered elements are { 11, 21, 3 }

-------------------------------------------------------------------------------
Usage of UnorderedRangeEquals range matcher
Custom predicate
Different element types keep predicate argument order
-------------------------------------------------------------------------------
MatchersRanges.tests.cpp:<line number>
...............................................................................

MatchersRanges.tests.cpp:<line number>: PASSED:
CHECK_THAT( actual, UnorderedRangeEquals( expected, []( UnorderedRangeActual const& lhs, UnorderedRangeExpected const& rhs ) { return lhs.value == rhs.value; } ) )
with expansion:
{ 1, 2, 3, 4 } unordered elements are { 4, 2, 3, 1 }

-------------------------------------------------------------------------------
Usage of UnorderedRangeEquals range matcher
Ranges that need ADL begin/end
Expand Down Expand Up @@ -20124,5 +20137,5 @@ Misc.tests.cpp:<line number>: PASSED:

===============================================================================
test cases: 451 | 331 passed | 96 failed | 6 skipped | 18 failed as expected
assertions: 2416 | 2215 passed | 158 failed | 43 failed as expected
assertions: 2417 | 2216 passed | 158 failed | 43 failed as expected

3 changes: 2 additions & 1 deletion tests/SelfTest/Baselines/junit.sw.approved.txt
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<?xml version="1.0" encoding="UTF-8"?>
<testsuitesloose text artifact
>
<testsuite name="<exe-name>" errors="17" failures="141" skipped="12" tests="2428" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
<testsuite name="<exe-name>" errors="17" failures="141" skipped="12" tests="2429" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
<properties>
<property name="random-seed" value="1"/>
<property name="filters" value="&quot;*&quot; ~[!nonportable] ~[!benchmark] ~[approvals]"/>
Expand Down Expand Up @@ -1417,6 +1417,7 @@ at Message.tests.cpp:<line number>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Custom predicate" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Two equal non-empty containers (close enough)" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Two non-equal non-empty containers (close enough)" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Different element types keep predicate argument order" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Ranges that need ADL begin/end" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Compare against std::initializer_list" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of the SizeIs range matcher" time="{duration}" status="run"/>
Expand Down
3 changes: 2 additions & 1 deletion tests/SelfTest/Baselines/junit.sw.multi.approved.txt
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<testsuites>
<testsuite name="<exe-name>" errors="17" failures="141" skipped="12" tests="2428" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
<testsuite name="<exe-name>" errors="17" failures="141" skipped="12" tests="2429" hostname="tbd" time="{duration}" timestamp="{iso8601-timestamp}">
<properties>
<property name="random-seed" value="1"/>
<property name="filters" value="&quot;*&quot; ~[!nonportable] ~[!benchmark] ~[approvals]"/>
Expand Down Expand Up @@ -1416,6 +1416,7 @@ at Message.tests.cpp:<line number>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Custom predicate" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Two equal non-empty containers (close enough)" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Two non-equal non-empty containers (close enough)" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Different element types keep predicate argument order" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Ranges that need ADL begin/end" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of UnorderedRangeEquals range matcher/Compare against std::initializer_list" time="{duration}" status="run"/>
<testcase classname="<exe-name>.global" name="Usage of the SizeIs range matcher" time="{duration}" status="run"/>
Expand Down
1 change: 1 addition & 0 deletions tests/SelfTest/Baselines/sonarqube.sw.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -1709,6 +1709,7 @@ at Matchers.tests.cpp:<line number>
<testCase name="Usage of UnorderedRangeEquals range matcher/Custom predicate" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Two equal non-empty containers (close enough)" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Two non-equal non-empty containers (close enough)" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Different element types keep predicate argument order" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Ranges that need ADL begin/end" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Compare against std::initializer_list" duration="{duration}"/>
<testCase name="Usage of the SizeIs range matcher" duration="{duration}"/>
Expand Down
1 change: 1 addition & 0 deletions tests/SelfTest/Baselines/sonarqube.sw.multi.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -1708,6 +1708,7 @@ at Matchers.tests.cpp:<line number>
<testCase name="Usage of UnorderedRangeEquals range matcher/Custom predicate" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Two equal non-empty containers (close enough)" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Two non-equal non-empty containers (close enough)" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Custom predicate/Different element types keep predicate argument order" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Ranges that need ADL begin/end" duration="{duration}"/>
<testCase name="Usage of UnorderedRangeEquals range matcher/Compare against std::initializer_list" duration="{duration}"/>
<testCase name="Usage of the SizeIs range matcher" duration="{duration}"/>
Expand Down
4 changes: 3 additions & 1 deletion tests/SelfTest/Baselines/tap.sw.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -3888,6 +3888,8 @@ ok {test-number} - vector_a, UnorderedRangeEquals( vector_a_plus_1, close_enough
# Usage of UnorderedRangeEquals range matcher
ok {test-number} - vector_a, !UnorderedRangeEquals( vector_b, close_enough ) for: { 1, 10, 21 } not unordered elements are { 11, 21, 3 }
# Usage of UnorderedRangeEquals range matcher
ok {test-number} - actual, UnorderedRangeEquals( expected, []( UnorderedRangeActual const& lhs, UnorderedRangeExpected const& rhs ) { return lhs.value == rhs.value; } ) for: { 1, 2, 3, 4 } unordered elements are { 4, 2, 3, 1 }
# Usage of UnorderedRangeEquals range matcher
ok {test-number} - needs_adl1, UnorderedRangeEquals( needs_adl2 ) for: { 1, 2, 3, 4, 5 } unordered elements are { 1, 2, 3, 4, 5 }
# Usage of UnorderedRangeEquals range matcher
ok {test-number} - array_a, UnorderedRangeEquals( { 10, 20, 1 } ) for: { 1, 10, 20 } unordered elements are { 10, 20, 1 }
Expand Down Expand Up @@ -4851,5 +4853,5 @@ ok {test-number} - q3 == 23. for: 23.0 == 23.0
ok {test-number} -
# xmlentitycheck
ok {test-number} -
1..2428
1..2429

4 changes: 3 additions & 1 deletion tests/SelfTest/Baselines/tap.sw.multi.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -3881,6 +3881,8 @@ ok {test-number} - vector_a, UnorderedRangeEquals( vector_a_plus_1, close_enough
# Usage of UnorderedRangeEquals range matcher
ok {test-number} - vector_a, !UnorderedRangeEquals( vector_b, close_enough ) for: { 1, 10, 21 } not unordered elements are { 11, 21, 3 }
# Usage of UnorderedRangeEquals range matcher
ok {test-number} - actual, UnorderedRangeEquals( expected, []( UnorderedRangeActual const& lhs, UnorderedRangeExpected const& rhs ) { return lhs.value == rhs.value; } ) for: { 1, 2, 3, 4 } unordered elements are { 4, 2, 3, 1 }
# Usage of UnorderedRangeEquals range matcher
ok {test-number} - needs_adl1, UnorderedRangeEquals( needs_adl2 ) for: { 1, 2, 3, 4, 5 } unordered elements are { 1, 2, 3, 4, 5 }
# Usage of UnorderedRangeEquals range matcher
ok {test-number} - array_a, UnorderedRangeEquals( { 10, 20, 1 } ) for: { 1, 10, 20 } unordered elements are { 10, 20, 1 }
Expand Down Expand Up @@ -4840,5 +4842,5 @@ ok {test-number} - q3 == 23. for: 23.0 == 23.0
ok {test-number} -
# xmlentitycheck
ok {test-number} -
1..2428
1..2429

16 changes: 15 additions & 1 deletion tests/SelfTest/Baselines/xml.sw.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -18919,6 +18919,20 @@ There is no extra whitespace here
</Section>
<OverallResults successes="1" failures="0" expectedFailures="0" skipped="false"/>
</Section>
<Section name="Custom predicate" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Section name="Different element types keep predicate argument order" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Original>
actual, UnorderedRangeEquals( expected, []( UnorderedRangeActual const&amp; lhs, UnorderedRangeExpected const&amp; rhs ) { return lhs.value == rhs.value; } )
</Original>
<Expanded>
{ 1, 2, 3, 4 } unordered elements are { 4, 2, 3, 1 }
</Expanded>
</Expression>
<OverallResults successes="1" failures="0" expectedFailures="0" skipped="false"/>
</Section>
<OverallResults successes="1" failures="0" expectedFailures="0" skipped="false"/>
</Section>
<Section name="Ranges that need ADL begin/end" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Expression success="true" type="REQUIRE_THAT" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Original>
Expand Down Expand Up @@ -23385,6 +23399,6 @@ Approx( -1.95996398454005449 )
</Section>
<OverallResult success="true" skips="0"/>
</TestCase>
<OverallResults successes="2215" failures="158" expectedFailures="43" skips="12"/>
<OverallResults successes="2216" failures="158" expectedFailures="43" skips="12"/>
<OverallResultsCases successes="331" failures="96" expectedFailures="18" skips="6"/>
</Catch2TestRun>
16 changes: 15 additions & 1 deletion tests/SelfTest/Baselines/xml.sw.multi.approved.txt
Original file line number Diff line number Diff line change
Expand Up @@ -18919,6 +18919,20 @@ There is no extra whitespace here
</Section>
<OverallResults successes="1" failures="0" expectedFailures="0" skipped="false"/>
</Section>
<Section name="Custom predicate" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Section name="Different element types keep predicate argument order" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Expression success="true" type="CHECK_THAT" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Original>
actual, UnorderedRangeEquals( expected, []( UnorderedRangeActual const&amp; lhs, UnorderedRangeExpected const&amp; rhs ) { return lhs.value == rhs.value; } )
</Original>
<Expanded>
{ 1, 2, 3, 4 } unordered elements are { 4, 2, 3, 1 }
</Expanded>
</Expression>
<OverallResults successes="1" failures="0" expectedFailures="0" skipped="false"/>
</Section>
<OverallResults successes="1" failures="0" expectedFailures="0" skipped="false"/>
</Section>
<Section name="Ranges that need ADL begin/end" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Expression success="true" type="REQUIRE_THAT" filename="tests/<exe-name>/UsageTests/MatchersRanges.tests.cpp" >
<Original>
Expand Down Expand Up @@ -23384,6 +23398,6 @@ Approx( -1.95996398454005449 )
</Section>
<OverallResult success="true" skips="0"/>
</TestCase>
<OverallResults successes="2215" failures="158" expectedFailures="43" skips="12"/>
<OverallResults successes="2216" failures="158" expectedFailures="43" skips="12"/>
<OverallResultsCases successes="331" failures="96" expectedFailures="18" skips="6"/>
</Catch2TestRun>
Loading