diff --git a/CMakeLists.txt b/CMakeLists.txt
index bf59b7d7..e1a26e05 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -6,7 +6,7 @@ if(NOT DEFINED PROJECT_NAME)
set(NOT_SUBPROJECT ON)
endif()
-project(Catch2 LANGUAGES CXX VERSION 2.8.0)
+project(Catch2 LANGUAGES CXX VERSION 2.9.0)
if (CMAKE_BINARY_DIR STREQUAL CMAKE_SOURCE_DIR)
message(FATAL_ERROR "Building in-source is not supported! Create a build dir and remove ${CMAKE_SOURCE_DIR}/CMakeCache.txt")
diff --git a/README.md b/README.md
index 47269cea..64308ee5 100644
--- a/README.md
+++ b/README.md
@@ -5,11 +5,11 @@
[](https://travis-ci.org/catchorg/Catch2)
[](https://ci.appveyor.com/project/catchorg/catch2)
[](https://codecov.io/gh/catchorg/Catch2)
-[](https://wandbox.org/permlink/wQeSudewoh6pdgRp)
+[](https://wandbox.org/permlink/HbqvzsGh9s9aubN3)
[](https://discord.gg/4CWS9zD)
-The latest version of the single header can be downloaded directly using this link
+The latest version of the single header can be downloaded directly using this link
## Catch2 is released!
diff --git a/docs/release-notes.md b/docs/release-notes.md
index c998b354..28388ebe 100644
--- a/docs/release-notes.md
+++ b/docs/release-notes.md
@@ -2,6 +2,7 @@
# Release notes
**Contents**
+[2.9.0](#290)
[2.8.0](#280)
[2.7.2](#272)
[2.7.1](#271)
@@ -24,6 +25,16 @@
[Older versions](#older-versions)
[Even Older versions](#even-older-versions)
+## 2.9.0
+
+### Improvements
+* The experimental benchmarking support has been replaced by integrating Nonius code (#1616)
+ * This provides a much more featurefull micro-benchmarking support.
+ * Due to the compilation cost, it is disabled by default. See the documentation for details.
+ * As far as backwards compatibility is concerned, this feature is still considered experimental in that we might change the interface based on user feedback.
+* `WithinULP` matcher now shows the acceptable range (#1581)
+* Template test cases now support type lists (#1627)
+
## 2.8.0
diff --git a/include/catch.hpp b/include/catch.hpp
index 483096b1..b63cc7fe 100644
--- a/include/catch.hpp
+++ b/include/catch.hpp
@@ -10,7 +10,7 @@
#define TWOBLUECUBES_CATCH_HPP_INCLUDED
#define CATCH_VERSION_MAJOR 2
-#define CATCH_VERSION_MINOR 8
+#define CATCH_VERSION_MINOR 9
#define CATCH_VERSION_PATCH 0
#ifdef __clang__
diff --git a/include/internal/catch_version.cpp b/include/internal/catch_version.cpp
index e5f683b2..b0fcb115 100644
--- a/include/internal/catch_version.cpp
+++ b/include/internal/catch_version.cpp
@@ -37,7 +37,7 @@ namespace Catch {
}
Version const& libraryVersion() {
- static Version version( 2, 8, 0, "", 0 );
+ static Version version( 2, 9, 0, "", 0 );
return version;
}
diff --git a/single_include/catch2/catch.hpp b/single_include/catch2/catch.hpp
index 02302b8d..9b145059 100644
--- a/single_include/catch2/catch.hpp
+++ b/single_include/catch2/catch.hpp
@@ -1,6 +1,6 @@
/*
- * Catch v2.8.0
- * Generated: 2019-05-26 21:29:22.235281
+ * Catch v2.9.0
+ * Generated: 2019-06-16 10:41:32.122746
* ----------------------------------------------------------
* This file has been merged from multiple headers. Please don't edit it directly
* Copyright (c) 2019 Two Blue Cubes Ltd. All rights reserved.
@@ -14,7 +14,7 @@
#define CATCH_VERSION_MAJOR 2
-#define CATCH_VERSION_MINOR 8
+#define CATCH_VERSION_MINOR 9
#define CATCH_VERSION_PATCH 0
#ifdef __clang__
@@ -210,9 +210,9 @@ namespace Catch {
// some versions of cygwin (most) do not support std::to_string. Use the libstd check.
// https://gcc.gnu.org/onlinedocs/gcc-4.8.2/libstdc++/api/a01053_source.html line 2812-2813
# if !((__cplusplus >= 201103L) && defined(_GLIBCXX_USE_C99) \
- && !defined(_GLIBCXX_HAVE_BROKEN_VSWPRINTF))
+ && !defined(_GLIBCXX_HAVE_BROKEN_VSWPRINTF))
-# define CATCH_INTERNAL_CONFIG_NO_CPP11_TO_STRING
+# define CATCH_INTERNAL_CONFIG_NO_CPP11_TO_STRING
# endif
#endif // __CYGWIN__
@@ -239,7 +239,11 @@ namespace Catch {
# if !defined(_MSVC_TRADITIONAL) || (defined(_MSVC_TRADITIONAL) && _MSVC_TRADITIONAL)
# define CATCH_INTERNAL_CONFIG_TRADITIONAL_MSVC_PREPROCESSOR
# endif
+#endif // _MSC_VER
+#if defined(_REENTRANT) || defined(_MSC_VER)
+// Enable async processing, as -pthread is specified or no additional linking is required
+# define CATCH_INTERNAL_CONFIG_USE_ASYNC
#endif // _MSC_VER
////////////////////////////////////////////////////////////////////////////////
@@ -358,6 +362,10 @@ namespace Catch {
# define CATCH_CONFIG_POLYFILL_ISNAN
#endif
+#if defined(CATCH_INTERNAL_CONFIG_USE_ASYNC) && !defined(CATCH_CONFIG_NO_USE_ASYNC) && !defined(CATCH_CONFIG_USE_ASYNC)
+# define CATCH_CONFIG_USE_ASYNC
+#endif
+
#if !defined(CATCH_INTERNAL_SUPPRESS_PARENTHESES_WARNINGS)
# define CATCH_INTERNAL_SUPPRESS_PARENTHESES_WARNINGS
# define CATCH_INTERNAL_UNSUPPRESS_PARENTHESES_WARNINGS
@@ -771,6 +779,8 @@ struct is_unique : std::integral_constant
constexpr auto append(L1, L2) noexcept -> L1 { return {}; }\
template< template class L1, typename...E1, template class L2, typename...E2, typename...Rest>\
constexpr auto append(L1, L2, Rest...) noexcept -> decltype(append(L1{}, Rest{}...)) { return {}; }\
+ template< template class L1, typename...E1, typename...Rest>\
+ constexpr auto append(L1, TypeList, Rest...) noexcept -> L1 { return {}; }\
\
template< template class Container, template class List, typename...elems>\
constexpr auto rewrap(List) noexcept -> TypeList> { return {}; }\
@@ -778,7 +788,9 @@ struct is_unique : std::integral_constant
constexpr auto rewrap(List,Elements...) noexcept -> decltype(append(TypeList>{}, rewrap(Elements{}...))) { return {}; }\
\
template class Final, template< typename...> class...Containers, typename...Types>\
- constexpr auto create(TypeList) noexcept -> decltype(append(Final<>{}, rewrap(Types{}...)...)) { return {}; }
+ constexpr auto create(TypeList) noexcept -> decltype(append(Final<>{}, rewrap(Types{}...)...)) { return {}; }\
+ template class Final, template class List, typename...Ts>\
+ constexpr auto convert(List) noexcept -> decltype(append(Final<>{},TypeList{}...)) { return {}; }
#define INTERNAL_CATCH_NTTP_1(signature, ...)\
template struct Nttp{};\
@@ -886,10 +898,29 @@ struct is_unique : std::integral_constant
#include
namespace Catch {
- template
- struct always_false : std::false_type {};
+template
+struct always_false : std::false_type {};
+
+template struct true_given : std::true_type {};
+struct is_callable_tester {
+ template
+ true_given()(std::declval()...))> static test(int);
+ template
+ std::false_type static test(...);
+};
+
+template
+struct is_callable;
+
+template
+struct is_callable : decltype(is_callable_tester::test(0)) {};
+
} // namespace Catch
+namespace mpl_{
+ struct na;
+}
+
// end catch_meta.hpp
namespace Catch {
@@ -1107,6 +1138,34 @@ struct AutoReg : NonCopyable {
INTERNAL_CATCH_EXPAND_VARGS( INTERNAL_CATCH_TEMPLATE_PRODUCT_TEST_CASE2( INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_M_P_L_A_T_E____T_E_S_T____ ), INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_M_P_L_A_T_E____T_E_S_T____F_U_N_C____ ), Name, Tags, Signature, __VA_ARGS__ ) )
#endif
+ #define INTERNAL_CATCH_TEMPLATE_LIST_TEST_CASE_2(TestName, TestFunc, Name, Tags, TmplList)\
+ CATCH_INTERNAL_SUPPRESS_GLOBALS_WARNINGS \
+ template static void TestFunc(); \
+ namespace {\
+ namespace INTERNAL_CATCH_MAKE_NAMESPACE(TestName){\
+ INTERNAL_CATCH_TYPE_GEN\
+ template \
+ struct TestName { \
+ void reg_tests() { \
+ int index = 0; \
+ using expander = int[]; \
+ (void)expander{(Catch::AutoReg( Catch::makeTestInvoker( &TestFunc ), CATCH_INTERNAL_LINEINFO, Catch::StringRef(), Catch::NameAndTags{ Name " - " + std::string(INTERNAL_CATCH_STRINGIZE(TmplList)) + " - " + std::to_string(index), Tags } ), index++, 0)... };/* NOLINT */\
+ } \
+ };\
+ static int INTERNAL_CATCH_UNIQUE_NAME( globalRegistrar ) = [](){ \
+ using TestInit = decltype(convert(TmplList {})); \
+ TestInit t; \
+ t.reg_tests(); \
+ return 0; \
+ }(); \
+ }}\
+ CATCH_INTERNAL_UNSUPPRESS_GLOBALS_WARNINGS \
+ template \
+ static void TestFunc()
+
+ #define INTERNAL_CATCH_TEMPLATE_LIST_TEST_CASE(Name, Tags, TmplList) \
+ INTERNAL_CATCH_TEMPLATE_LIST_TEST_CASE_2( INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_M_P_L_A_T_E____T_E_S_T____ ), INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_M_P_L_A_T_E____T_E_S_T____F_U_N_C____ ), Name, Tags, TmplList )
+
#define INTERNAL_CATCH_TEMPLATE_TEST_CASE_METHOD_2( TestNameClass, TestName, ClassName, Name, Tags, Signature, ... ) \
CATCH_INTERNAL_SUPPRESS_GLOBALS_WARNINGS \
CATCH_INTERNAL_SUPPRESS_ZERO_VARIADIC_WARNINGS \
@@ -1202,6 +1261,37 @@ struct AutoReg : NonCopyable {
INTERNAL_CATCH_EXPAND_VARGS( INTERNAL_CATCH_TEMPLATE_PRODUCT_TEST_CASE_METHOD_2( INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_M_P_L_A_T_E____T_E_S_T____ ), INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_M_P_L_A_T_E____T_E_S_T____F_U_N_C____ ), ClassName, Name, Tags, Signature,__VA_ARGS__ ) )
#endif
+ #define INTERNAL_CATCH_TEMPLATE_LIST_TEST_CASE_METHOD_2( TestNameClass, TestName, ClassName, Name, Tags, TmplList) \
+ CATCH_INTERNAL_SUPPRESS_GLOBALS_WARNINGS \
+ template \
+ struct TestName : INTERNAL_CATCH_REMOVE_PARENS(ClassName ) { \
+ void test();\
+ };\
+ namespace {\
+ namespace INTERNAL_CATCH_MAKE_NAMESPACE(TestName){ \
+ INTERNAL_CATCH_TYPE_GEN\
+ template\
+ struct TestNameClass{\
+ void reg_tests(){\
+ int index = 0;\
+ using expander = int[];\
+ (void)expander{(Catch::AutoReg( Catch::makeTestInvoker( &TestName::test ), CATCH_INTERNAL_LINEINFO, #ClassName, Catch::NameAndTags{ Name " - " + std::string(INTERNAL_CATCH_STRINGIZE(TmplList)) + " - " + std::to_string(index), Tags } ), index++, 0)... };/* NOLINT */ \
+ }\
+ };\
+ static int INTERNAL_CATCH_UNIQUE_NAME( globalRegistrar ) = [](){\
+ using TestInit = decltype(convert(TmplList {}));\
+ TestInit t;\
+ t.reg_tests();\
+ return 0;\
+ }(); \
+ }}\
+ CATCH_INTERNAL_UNSUPPRESS_GLOBALS_WARNINGS \
+ template \
+ void TestName::test()
+
+#define INTERNAL_CATCH_TEMPLATE_LIST_TEST_CASE_METHOD(ClassName, Name, Tags, TmplList) \
+ INTERNAL_CATCH_TEMPLATE_LIST_TEST_CASE_METHOD_2( INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_M_P_L_A_T_E____T_E_S_T____ ), INTERNAL_CATCH_UNIQUE_NAME( ____C_A_T_C_H____T_E_M_P_L_A_T_E____T_E_S_T____F_U_N_C____ ), ClassName, Name, Tags, TmplList )
+
// end catch_test_registry.h
// start catch_capture.hpp
@@ -2270,6 +2360,7 @@ namespace Catch {
// start catch_interfaces_capture.h
#include
+#include
namespace Catch {
@@ -2280,14 +2371,18 @@ namespace Catch {
struct MessageInfo;
struct MessageBuilder;
struct Counts;
- struct BenchmarkInfo;
- struct BenchmarkStats;
struct AssertionReaction;
struct SourceLineInfo;
struct ITransientExpression;
struct IGeneratorTracker;
+#if defined(CATCH_CONFIG_ENABLE_BENCHMARKING)
+ struct BenchmarkInfo;
+ template >
+ struct BenchmarkStats;
+#endif // CATCH_CONFIG_ENABLE_BENCHMARKING
+
struct IResultCapture {
virtual ~IResultCapture();
@@ -2299,8 +2394,12 @@ namespace Catch {
virtual auto acquireGeneratorTracker( SourceLineInfo const& lineInfo ) -> IGeneratorTracker& = 0;
+#if defined(CATCH_CONFIG_ENABLE_BENCHMARKING)
+ virtual void benchmarkPreparing( std::string const& name ) = 0;
virtual void benchmarkStarting( BenchmarkInfo const& info ) = 0;
- virtual void benchmarkEnded( BenchmarkStats const& stats ) = 0;
+ virtual void benchmarkEnded( BenchmarkStats<> const& stats ) = 0;
+ virtual void benchmarkFailed( std::string const& error ) = 0;
+#endif // CATCH_CONFIG_ENABLE_BENCHMARKING
virtual void pushScopedMessage( MessageInfo const& message ) = 0;
virtual void popScopedMessage( MessageInfo const& message ) = 0;
@@ -2766,52 +2865,6 @@ namespace Catch {
CATCH_INTERNAL_UNSUPPRESS_UNUSED_WARNINGS
// end catch_section.h
-// start catch_benchmark.h
-
-#include
-#include
-
-namespace Catch {
-
- class BenchmarkLooper {
-
- std::string m_name;
- std::size_t m_count = 0;
- std::size_t m_iterationsToRun = 1;
- uint64_t m_resolution;
- Timer m_timer;
-
- static auto getResolution() -> uint64_t;
- public:
- // Keep most of this inline as it's on the code path that is being timed
- BenchmarkLooper( StringRef name )
- : m_name( name ),
- m_resolution( getResolution() )
- {
- reportStart();
- m_timer.start();
- }
-
- explicit operator bool() {
- if( m_count < m_iterationsToRun )
- return true;
- return needsMoreIterations();
- }
-
- void increment() {
- ++m_count;
- }
-
- void reportStart();
- auto needsMoreIterations() -> bool;
- };
-
-} // end namespace Catch
-
-#define BENCHMARK( name ) \
- for( Catch::BenchmarkLooper looper( name ); looper; looper.increment() )
-
-// end catch_benchmark.h
// start catch_interfaces_exception.h
// start catch_interfaces_registry_hub.h
@@ -3678,7 +3731,7 @@ namespace Catch {
// end catch_interfaces_generatortracker.h
// start catch_enforce.h
-#include
+#include
namespace Catch {
#if !defined(CATCH_CONFIG_DISABLE_EXCEPTIONS)
@@ -3691,18 +3744,30 @@ namespace Catch {
[[noreturn]]
void throw_exception(std::exception const& e);
#endif
+
+ [[noreturn]]
+ void throw_logic_error(std::string const& msg);
+ [[noreturn]]
+ void throw_domain_error(std::string const& msg);
+ [[noreturn]]
+ void throw_runtime_error(std::string const& msg);
+
} // namespace Catch;
-#define CATCH_PREPARE_EXCEPTION( type, msg ) \
- type( ( Catch::ReusableStringStream() << msg ).str() )
-#define CATCH_INTERNAL_ERROR( msg ) \
- Catch::throw_exception(CATCH_PREPARE_EXCEPTION( std::logic_error, CATCH_INTERNAL_LINEINFO << ": Internal Catch error: " << msg))
-#define CATCH_ERROR( msg ) \
- Catch::throw_exception(CATCH_PREPARE_EXCEPTION( std::domain_error, msg ))
-#define CATCH_RUNTIME_ERROR( msg ) \
- Catch::throw_exception(CATCH_PREPARE_EXCEPTION( std::runtime_error, msg ))
-#define CATCH_ENFORCE( condition, msg ) \
- do{ if( !(condition) ) CATCH_ERROR( msg ); } while(false)
+#define CATCH_MAKE_MSG(...) \
+ (Catch::ReusableStringStream() << __VA_ARGS__).str()
+
+#define CATCH_INTERNAL_ERROR(...) \
+ Catch::throw_logic_error(CATCH_MAKE_MSG( CATCH_INTERNAL_LINEINFO << ": Internal Catch2 error: " << __VA_ARGS__));
+
+#define CATCH_ERROR(...) \
+ Catch::throw_domain_error(CATCH_MAKE_MSG( __VA_ARGS__ ));
+
+#define CATCH_RUNTIME_ERROR(...) \
+ Catch::throw_runtime_error(CATCH_MAKE_MSG( __VA_ARGS__ ));
+
+#define CATCH_ENFORCE( condition, ... ) \
+ do{ if( !(condition) ) CATCH_ERROR( __VA_ARGS__ ); } while(false)
// end catch_enforce.h
#include
@@ -4187,6 +4252,71 @@ namespace Catch {
// end catch_context.h
// start catch_interfaces_config.h
+// start catch_option.hpp
+
+namespace Catch {
+
+ // An optional type
+ template
+ class Option {
+ public:
+ Option() : nullableValue( nullptr ) {}
+ Option( T const& _value )
+ : nullableValue( new( storage ) T( _value ) )
+ {}
+ Option( Option const& _other )
+ : nullableValue( _other ? new( storage ) T( *_other ) : nullptr )
+ {}
+
+ ~Option() {
+ reset();
+ }
+
+ Option& operator= ( Option const& _other ) {
+ if( &_other != this ) {
+ reset();
+ if( _other )
+ nullableValue = new( storage ) T( *_other );
+ }
+ return *this;
+ }
+ Option& operator = ( T const& _value ) {
+ reset();
+ nullableValue = new( storage ) T( _value );
+ return *this;
+ }
+
+ void reset() {
+ if( nullableValue )
+ nullableValue->~T();
+ nullableValue = nullptr;
+ }
+
+ T& operator*() { return *nullableValue; }
+ T const& operator*() const { return *nullableValue; }
+ T* operator->() { return nullableValue; }
+ const T* operator->() const { return nullableValue; }
+
+ T valueOr( T const& defaultValue ) const {
+ return nullableValue ? *nullableValue : defaultValue;
+ }
+
+ bool some() const { return nullableValue != nullptr; }
+ bool none() const { return nullableValue == nullptr; }
+
+ bool operator !() const { return nullableValue == nullptr; }
+ explicit operator bool() const {
+ return some();
+ }
+
+ private:
+ T *nullableValue;
+ alignas(alignof(T)) char storage[sizeof(T)];
+ };
+
+} // end namespace Catch
+
+// end catch_option.hpp
#include
#include
#include
@@ -4249,10 +4379,14 @@ namespace Catch {
virtual std::vector const& getTestsOrTags() const = 0;
virtual RunTests::InWhatOrder runOrder() const = 0;
virtual unsigned int rngSeed() const = 0;
- virtual int benchmarkResolutionMultiple() const = 0;
virtual UseColour::YesOrNo useColour() const = 0;
virtual std::vector const& getSectionsToRun() const = 0;
virtual Verbosity verbosity() const = 0;
+
+ virtual bool benchmarkNoAnalysis() const = 0;
+ virtual int benchmarkSamples() const = 0;
+ virtual double benchmarkConfidenceInterval() const = 0;
+ virtual unsigned int benchmarkResamples() const = 0;
};
using IConfigPtr = std::shared_ptr;
@@ -4894,7 +5028,11 @@ namespace Catch {
int abortAfter = -1;
unsigned int rngSeed = 0;
- int benchmarkResolutionMultiple = 100;
+
+ bool benchmarkNoAnalysis = false;
+ unsigned int benchmarkSamples = 100;
+ double benchmarkConfidenceInterval = 0.95;
+ unsigned int benchmarkResamples = 100000;
Verbosity verbosity = Verbosity::Normal;
WarnAbout::What warnings = WarnAbout::Nothing;
@@ -4951,12 +5089,15 @@ namespace Catch {
ShowDurations::OrNot showDurations() const override;
RunTests::InWhatOrder runOrder() const override;
unsigned int rngSeed() const override;
- int benchmarkResolutionMultiple() const override;
UseColour::YesOrNo useColour() const override;
bool shouldDebugBreak() const override;
int abortAfter() const override;
bool showInvisibles() const override;
Verbosity verbosity() const override;
+ bool benchmarkNoAnalysis() const override;
+ int benchmarkSamples() const override;
+ double benchmarkConfidenceInterval() const override;
+ unsigned int benchmarkResamples() const override;
private:
@@ -5017,76 +5158,59 @@ namespace Catch {
} // end namespace Catch
// end catch_assertionresult.h
-// start catch_option.hpp
+#if defined(CATCH_CONFIG_ENABLE_BENCHMARKING)
+// start catch_estimate.hpp
+
+ // Statistics estimates
+
namespace Catch {
+ namespace Benchmark {
+ template
+ struct Estimate {
+ Duration point;
+ Duration lower_bound;
+ Duration upper_bound;
+ double confidence_interval;
- // An optional type
- template
- class Option {
- public:
- Option() : nullableValue( nullptr ) {}
- Option( T const& _value )
- : nullableValue( new( storage ) T( _value ) )
- {}
- Option( Option const& _other )
- : nullableValue( _other ? new( storage ) T( *_other ) : nullptr )
- {}
-
- ~Option() {
- reset();
- }
-
- Option& operator= ( Option const& _other ) {
- if( &_other != this ) {
- reset();
- if( _other )
- nullableValue = new( storage ) T( *_other );
+ template
+ operator Estimate() const {
+ return { point, lower_bound, upper_bound, confidence_interval };
}
- return *this;
- }
- Option& operator = ( T const& _value ) {
- reset();
- nullableValue = new( storage ) T( _value );
- return *this;
- }
+ };
+ } // namespace Benchmark
+} // namespace Catch
- void reset() {
- if( nullableValue )
- nullableValue->~T();
- nullableValue = nullptr;
- }
+// end catch_estimate.hpp
+// start catch_outlier_classification.hpp
- T& operator*() { return *nullableValue; }
- T const& operator*() const { return *nullableValue; }
- T* operator->() { return nullableValue; }
- const T* operator->() const { return nullableValue; }
+// Outlier information
- T valueOr( T const& defaultValue ) const {
- return nullableValue ? *nullableValue : defaultValue;
- }
+namespace Catch {
+ namespace Benchmark {
+ struct OutlierClassification {
+ int samples_seen = 0;
+ int low_severe = 0; // more than 3 times IQR below Q1
+ int low_mild = 0; // 1.5 to 3 times IQR below Q1
+ int high_mild = 0; // 1.5 to 3 times IQR above Q3
+ int high_severe = 0; // more than 3 times IQR above Q3
- bool some() const { return nullableValue != nullptr; }
- bool none() const { return nullableValue == nullptr; }
+ int total() const {
+ return low_severe + low_mild + high_mild + high_severe;
+ }
+ };
+ } // namespace Benchmark
+} // namespace Catch
- bool operator !() const { return nullableValue == nullptr; }
- explicit operator bool() const {
- return some();
- }
+// end catch_outlier_classification.hpp
+#endif // CATCH_CONFIG_ENABLE_BENCHMARKING
- private:
- T *nullableValue;
- alignas(alignof(T)) char storage[sizeof(T)];
- };
-
-} // end namespace Catch
-
-// end catch_option.hpp
#include
#include
#include