OpenDDS  Snapshot(2023/04/28-20:55)
SafeBool_T.h
Go to the documentation of this file.
1 /**
2  * \file
3  * Implements the "Safe Bool" idiom, which is a safer alternative to operator
4  * bool. Based on:
5  * https://www.artima.com/articles/the-safe-bool-idiom
6  * TLDR: We may want to be able to use `operator bool()` to check an object's
7  * abstract truthfulness using `if (object) {...}`, but that opens up implicit
8  * casting and comparisons that come with the bool type that are almost
9  * certainly not desired, like `int count = object`. This is achieved via the
10  * BoolType function pointer which isn't actually called, but is the only
11  * boolean-ish thing the type can be implicitly converted to using the BoolType
12  * operator.
13  *
14  * If you want the boolean test function to be virtual, implement it as:
15  * virtual bool boolean_test() const;
16  * and derive the class from SafeBool_T with no template argument:
17  * class YourClass : public SafeBool_T<>.
18  *
19  * If you do NOT want the boolean test function to be virtual, implement it as:
20  * bool boolean_test() const;
21  * and derive the class from SafeBool_T with the class as the template argument:
22  * class YourClass : public SafeBool_T<YourClass>.
23  */
24 
25 #ifndef OPENDDS_DCPS_SAFE_BOOL_T_H
26 #define OPENDDS_DCPS_SAFE_BOOL_T_H
27 
29 
31 
32 namespace OpenDDS {
33 namespace DCPS {
34 
35 class SafeBoolBase {
36 public:
37  typedef void (SafeBoolBase::*BoolType)() const;
39 
40 protected:
43  SafeBoolBase& operator=(const SafeBoolBase&) {return *this;}
45 };
46 
47 template <typename DerivedNonVirtual = void>
48 class SafeBool_T : public SafeBoolBase {
49 public:
50  operator BoolType() const
51  {
52  return (static_cast<const DerivedNonVirtual*>(this))->boolean_test()
54  }
55 
56 protected:
58 };
59 
60 template<>
61 class SafeBool_T<void> : public SafeBoolBase {
62 public:
63  operator BoolType() const
64  {
65  return boolean_test() ?
67  }
68 
69 protected:
70  virtual bool boolean_test() const = 0;
71  virtual ~SafeBool_T() {}
72 };
73 
74 template <typename X, typename Y>
75 bool operator==(const SafeBool_T<X>& x, const SafeBool_T<Y>&)
76 {
78  return false;
79 }
80 
81 template <typename X, typename Y>
82 bool operator!=(const SafeBool_T<X>& x, const SafeBool_T<Y>&)
83 {
85  return false;
86 }
87 
88 } // namespace DCPS
89 } // namespace OpenDDS
90 
92 
93 #endif
bool operator==(const DisjointSequence::OrderedRanges< T > &a, const DisjointSequence::OrderedRanges< T > &b)
void this_type_does_not_support_comparisons() const
Definition: SafeBool_T.h:38
SafeBoolBase & operator=(const SafeBoolBase &)
Definition: SafeBool_T.h:43
SafeBoolBase(const SafeBoolBase &)
Definition: SafeBool_T.h:42
void(SafeBoolBase::* BoolType)() const
Definition: SafeBool_T.h:37
bool operator!=(const GUID_t &lhs, const GUID_t &rhs)
Definition: GuidUtils.h:125
#define OPENDDS_END_VERSIONED_NAMESPACE_DECL
The Internal API and Implementation of OpenDDS.
Definition: AddressCache.h:28