33 #ifndef GKO_CORE_BASE_POLYMORPHIC_OBJECT_HPP_ 34 #define GKO_CORE_BASE_POLYMORPHIC_OBJECT_HPP_ 37 #include <ginkgo/core/base/executor.hpp> 38 #include <ginkgo/core/base/utils.hpp> 39 #include <ginkgo/core/log/logger.hpp> 71 this->
template log<log::Logger::polymorphic_object_deleted>(exec_.get(),
89 std::shared_ptr<const Executor> exec)
const 91 this->
template log<log::Logger::polymorphic_object_create_started>(
93 auto created = this->create_default_impl(std::move(exec));
94 this->
template log<log::Logger::polymorphic_object_create_completed>(
95 exec_.get(),
this, created.get());
122 std::unique_ptr<PolymorphicObject>
clone(
123 std::shared_ptr<const Executor> exec)
const 126 new_op->copy_from(
this);
138 std::unique_ptr<PolymorphicObject>
clone()
const 140 return this->
clone(exec_);
156 this->
template log<log::Logger::polymorphic_object_copy_started>(
157 exec_.get(), other,
this);
158 auto copied = this->copy_from_impl(other);
159 this->
template log<log::Logger::polymorphic_object_copy_completed>(
160 exec_.get(), other,
this);
177 this->
template log<log::Logger::polymorphic_object_copy_started>(
178 exec_.get(), other.get(),
this);
179 auto copied = this->copy_from_impl(std::move(other));
180 this->
template log<log::Logger::polymorphic_object_copy_completed>(
181 exec_.get(), other.get(),
this);
217 : exec_{std::move(exec)}
228 virtual std::unique_ptr<PolymorphicObject> create_default_impl(
229 std::shared_ptr<const Executor> exec)
const = 0;
251 std::unique_ptr<PolymorphicObject> other) = 0;
262 std::shared_ptr<const Executor> exec_;
284 template <
typename AbstactObject,
typename PolymorphicBase = PolymorphicObject>
287 using PolymorphicBase::PolymorphicBase;
290 std::shared_ptr<const Executor> exec)
const 292 return std::unique_ptr<AbstactObject>{
static_cast<AbstactObject *
>(
293 this->create_default_impl(std::move(exec)).release())};
301 std::unique_ptr<AbstactObject>
clone(
302 std::shared_ptr<const Executor> exec)
const 305 new_op->copy_from(
this);
309 std::unique_ptr<AbstactObject>
clone()
const 316 return static_cast<AbstactObject *
>(this->copy_from_impl(other));
319 AbstactObject *
copy_from(std::unique_ptr<PolymorphicObject> other)
321 return static_cast<AbstactObject *
>(
322 this->copy_from_impl(std::move(other)));
325 AbstactObject *
clear()
327 return static_cast<AbstactObject *
>(this->clear_impl());
340 #define GKO_ENABLE_SELF(_type) \ 341 _type *self() noexcept { return static_cast<_type *>(this); } \ 343 const _type *self() const noexcept \ 345 return static_cast<const _type *>(this); \ 379 template <
typename ResultType>
382 using result_type = ResultType;
391 virtual void convert_to(result_type *result)
const = 0;
407 virtual void move_to(result_type *result) = 0;
414 template <
typename R,
typename T>
415 std::unique_ptr<R, std::function<void(R *)>> copy_and_convert_to_impl(
416 std::shared_ptr<const Executor> exec, T *obj)
418 auto obj_as_r =
dynamic_cast<R *
>(obj);
419 if (obj_as_r !=
nullptr && obj->get_executor() == exec) {
420 return {obj_as_r, [](R *) {}};
422 auto copy = R::create(exec);
423 as<ConvertibleTo<xstd::decay_t<R>>>(obj)->convert_to(
lend(copy));
424 return {copy.release(), std::default_delete<R>{}};
448 template <
typename R,
typename T>
450 std::shared_ptr<const Executor> exec, T *obj)
452 return detail::copy_and_convert_to_impl<R>(std::move(exec), obj);
462 template <
typename R,
typename T>
464 std::shared_ptr<const Executor> exec,
const T *obj)
466 return detail::copy_and_convert_to_impl<const R>(std::move(exec), obj);
504 template <
typename ConcreteObject,
typename PolymorphicBase = PolymorphicObject>
511 std::unique_ptr<PolymorphicObject> create_default_impl(
512 std::shared_ptr<const Executor> exec)
const override 514 return std::unique_ptr<ConcreteObject>{
new ConcreteObject(exec)};
519 as<ConvertibleTo<ConcreteObject>>(other)->convert_to(
self());
524 std::unique_ptr<PolymorphicObject> other)
override 526 as<ConvertibleTo<ConcreteObject>>(other.get())->move_to(
self());
537 GKO_ENABLE_SELF(ConcreteObject);
553 template <
typename ConcreteType,
typename ResultType = ConcreteType>
556 using result_type = ResultType;
558 void convert_to(result_type *result)
const override { *result = *
self(); }
560 void move_to(result_type *result)
override { *result = std::move(*
self()); }
563 GKO_ENABLE_SELF(ConcreteType);
575 template <
typename ConcreteType>
578 template <
typename... Args>
579 static std::unique_ptr<ConcreteType> create(Args &&... args)
581 return std::unique_ptr<ConcreteType>(
582 new ConcreteType(std::forward<Args>(args)...));
590 #endif // GKO_CORE_BASE_POLYMORPHIC_OBJECT_HPP_ This mixin inherits from (a subclass of) PolymorphicObject and provides a base implementation of a ne...
Definition: polymorphic_object.hpp:285
std::unique_ptr< PolymorphicObject > clone(std::shared_ptr< const Executor > exec) const
Creates a clone of the object.
Definition: polymorphic_object.hpp:122
This mixin implements a static create() method on ConcreteType that dynamically allocates the memory...
Definition: polymorphic_object.hpp:576
ConvertibleTo interface is used to mark that the implementer can be converted to the object of Result...
Definition: polymorphic_object.hpp:380
This mixin inherits from (a subclass of) PolymorphicObject and provides a base implementation of a ne...
Definition: polymorphic_object.hpp:505
std::unique_ptr< PolymorphicObject > create_default(std::shared_ptr< const Executor > exec) const
Creates a new "default" object of the same dynamic type as this object.
Definition: polymorphic_object.hpp:88
PolymorphicObject * copy_from(std::unique_ptr< PolymorphicObject > other)
Moves another object into this object.
Definition: polymorphic_object.hpp:175
PolymorphicObject * clear()
Transforms the object into its default state.
Definition: polymorphic_object.hpp:194
std::unique_ptr< PolymorphicObject > create_default() const
Creates a new "default" object of the same dynamic type as this object.
Definition: polymorphic_object.hpp:107
std::unique_ptr< R, std::function< void(R *)> > copy_and_convert_to(std::shared_ptr< const Executor > exec, T *obj)
Converts the object to R and places it on Executor exec.
Definition: polymorphic_object.hpp:449
The Ginkgo namespace.
Definition: abstract_factory.hpp:45
PolymorphicObject * copy_from(const PolymorphicObject *other)
Copies another object into this object.
Definition: polymorphic_object.hpp:154
A PolymorphicObject is the abstract base for all "heavy" objects in Ginkgo that behave polymorphicall...
Definition: polymorphic_object.hpp:67
std::unique_ptr< PolymorphicObject > clone() const
Creates a clone of the object.
Definition: polymorphic_object.hpp:138
EnableLogging is a mixin which should be inherited by any class which wants to enable logging...
Definition: logger.hpp:521
void convert_to(result_type *result) const override
Converts the implementer to an object of type result_type.
Definition: polymorphic_object.hpp:558
void move_to(result_type *result) override
Converts the implementer to an object of type result_type by moving data from this object...
Definition: polymorphic_object.hpp:560
std::shared_ptr< const Executor > get_executor() const noexcept
Returns the Executor of the object.
Definition: polymorphic_object.hpp:201
std::enable_if< detail::have_ownership< Pointer >), detail::pointee< Pointer > * >::type lend(const Pointer &p)
Returns a non-owning (plain) pointer to the object pointed to by p.
Definition: utils.hpp:249
This mixin is used to enable a default PolymorphicObject::copy_from() implementation for objects that...
Definition: polymorphic_object.hpp:554