All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Pages
Cloneable.h
Go to the documentation of this file.
1 // Copyright 2015, 2016 Thomas Trapp
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14 
15 #ifndef HEXT_CLONEABLE_H_INCLUDED
16 #define HEXT_CLONEABLE_H_INCLUDED
17 
18 /// @file
19 /// Defines template hext::Cloneable
20 
21 #include "hext/Visibility.h"
22 
23 #include <memory>
24 #include <type_traits>
25 
26 
27 namespace hext {
28 
29 
30 /// Curiously recurring template pattern that extends a base class to provide
31 /// a virtual method Cloneable::clone().
32 ///
33 /// @tparam Derived: A subclass of Cloneable that is copy constructible.
34 /// @tparam Base: The base class that shall be extended.
35 template<typename Derived, typename Base>
36 class HEXT_PUBLIC Cloneable : public Base
37 {
38 public:
39  /// Clones objects of template type Derived and returns an owning pointer to
40  /// the newly allocated Base.
41  ///
42  /// Fails at compile time if template parameter Base is not a base of template
43  /// parameter Derived or if template parameter Derived is not copy
44  /// constructible.
45  virtual std::unique_ptr<Base> clone() const
46  {
47  static_assert(std::is_base_of<Base, Derived>::value,
48  "template argument <Base> is not a base of "
49  "template argument <Derived>");
50  static_assert(std::is_copy_constructible<Derived>::value,
51  "template argument <Derived> is not copy constructible");
52  // This static_cast is safe because we have just asserted that Derived is a
53  // subclass of Base.
54  return std::make_unique<Derived>(static_cast<const Derived&>(*this));
55  }
56 };
57 
58 
59 } // namespace hext
60 
61 
62 #endif // HEXT_CLONEABLE_H_INCLUDED
63 
virtual std::unique_ptr< Base > clone() const
Clones objects of template type Derived and returns an owning pointer to the newly allocated Base...
Definition: Cloneable.h:45
Defines HEXT_PUBLIC and HEXT_PRIVATE.
#define HEXT_PUBLIC
Definition: Visibility.h:26
Curiously recurring template pattern that extends a base class to provide a virtual method Cloneable:...
Definition: Cloneable.h:36