5 #ifndef GKO_PUBLIC_CORE_BASE_PRECISION_DISPATCH_HPP_
6 #define GKO_PUBLIC_CORE_BASE_PRECISION_DISPATCH_HPP_
9 #include <ginkgo/config.hpp>
10 #include <ginkgo/core/base/math.hpp>
11 #include <ginkgo/core/base/temporary_conversion.hpp>
12 #include <ginkgo/core/distributed/vector.hpp>
13 #include <ginkgo/core/matrix/dense.hpp>
43 template <
typename ValueType,
typename Ptr>
44 detail::temporary_conversion<std::conditional_t<
45 std::is_const<detail::pointee<Ptr>>::value,
const matrix::Dense<ValueType>,
46 matrix::Dense<ValueType>>>
49 using Pointee = detail::pointee<Ptr>;
52 using MaybeConstDense =
53 std::conditional_t<std::is_const<Pointee>::value,
const Dense, Dense>;
54 auto result = detail::temporary_conversion<
55 MaybeConstDense>::template create<NextDense>(matrix);
57 GKO_NOT_SUPPORTED(*matrix);
77 template <
typename ValueType,
typename Function,
typename... Args>
80 fn(make_temporary_conversion<ValueType>(linops).get()...);
93 template <
typename ValueType,
typename Function>
100 auto complex_to_real =
101 !(is_complex<ValueType>() ||
103 if (complex_to_real) {
104 auto dense_in = make_temporary_conversion<to_complex<ValueType>>(in);
105 auto dense_out = make_temporary_conversion<to_complex<ValueType>>(out);
110 fn(dynamic_cast<const Dense*>(dense_in->create_real_view().get()),
111 dynamic_cast<Dense*>(dense_out->create_real_view().get()));
113 precision_dispatch<ValueType>(fn, in, out);
127 template <
typename ValueType,
typename Function>
135 auto complex_to_real =
136 !(is_complex<ValueType>() ||
138 if (complex_to_real) {
139 auto dense_in = make_temporary_conversion<to_complex<ValueType>>(in);
140 auto dense_out = make_temporary_conversion<to_complex<ValueType>>(out);
141 auto dense_alpha = make_temporary_conversion<ValueType>(alpha);
146 fn(dense_alpha.get(),
147 dynamic_cast<const Dense*>(dense_in->create_real_view().get()),
148 dynamic_cast<Dense*>(dense_out->create_real_view().get()));
150 precision_dispatch<ValueType>(fn, alpha, in, out);
164 template <
typename ValueType,
typename Function>
173 auto complex_to_real =
174 !(is_complex<ValueType>() ||
176 if (complex_to_real) {
177 auto dense_in = make_temporary_conversion<to_complex<ValueType>>(in);
178 auto dense_out = make_temporary_conversion<to_complex<ValueType>>(out);
179 auto dense_alpha = make_temporary_conversion<ValueType>(alpha);
180 auto dense_beta = make_temporary_conversion<ValueType>(beta);
185 fn(dense_alpha.get(),
186 dynamic_cast<const Dense*>(dense_in->create_real_view().get()),
188 dynamic_cast<Dense*>(dense_out->create_real_view().get()));
190 precision_dispatch<ValueType>(fn, alpha, in, beta, out);
224 template <
typename ValueType,
typename Function>
227 #ifdef GINKGO_MIXED_PRECISION
230 if (
auto dense_in = dynamic_cast<const fst_type*>(in)) {
231 if (
auto dense_out = dynamic_cast<fst_type*>(out)) {
232 fn(dense_in, dense_out);
233 }
else if (
auto dense_out = dynamic_cast<snd_type*>(out)) {
234 fn(dense_in, dense_out);
236 GKO_NOT_SUPPORTED(out);
238 }
else if (
auto dense_in = dynamic_cast<const snd_type*>(in)) {
239 if (
auto dense_out = dynamic_cast<fst_type*>(out)) {
240 fn(dense_in, dense_out);
241 }
else if (
auto dense_out = dynamic_cast<snd_type*>(out)) {
242 fn(dense_in, dense_out);
244 GKO_NOT_SUPPORTED(out);
247 GKO_NOT_SUPPORTED(in);
250 precision_dispatch<ValueType>(fn, in, out);
264 template <
typename ValueType,
typename Function,
265 std::enable_if_t<is_complex<ValueType>()>* =
nullptr>
269 #ifdef GINKGO_MIXED_PRECISION
270 mixed_precision_dispatch<ValueType>(fn, in, out);
272 precision_dispatch<ValueType>(fn, in, out);
277 template <
typename ValueType,
typename Function,
278 std::enable_if_t<!is_complex<ValueType>()>* =
nullptr>
282 #ifdef GINKGO_MIXED_PRECISION
283 if (!
dynamic_cast<const ConvertibleTo<matrix::Dense<>
>*>(in)) {
284 mixed_precision_dispatch<to_complex<ValueType>>(
285 [&fn](
auto dense_in,
auto dense_out) {
286 fn(dense_in->create_real_view().get(),
287 dense_out->create_real_view().get());
291 mixed_precision_dispatch<ValueType>(fn, in, out);
294 precision_dispatch_real_complex<ValueType>(fn, in, out);
299 namespace experimental {
305 namespace distributed {
333 template <
typename ValueType>
334 detail::temporary_conversion<experimental::distributed::Vector<ValueType>>
337 auto result = detail::temporary_conversion<
343 GKO_NOT_SUPPORTED(matrix);
352 template <
typename ValueType>
353 detail::temporary_conversion<const experimental::distributed::Vector<ValueType>>
356 auto result = detail::temporary_conversion<
362 GKO_NOT_SUPPORTED(matrix);
382 template <
typename ValueType,
typename Function,
typename... Args>
385 fn(distributed::make_temporary_conversion<ValueType>(linops).get()...);
398 template <
typename ValueType,
typename Function>
401 auto complex_to_real = !(
402 is_complex<ValueType>() ||
405 if (complex_to_real) {
407 distributed::make_temporary_conversion<to_complex<ValueType>>(in);
409 distributed::make_temporary_conversion<to_complex<ValueType>>(out);
414 fn(dynamic_cast<const Vector*>(dense_in->create_real_view().get()),
415 dynamic_cast<Vector*>(dense_out->create_real_view().get()));
417 distributed::precision_dispatch<ValueType>(fn, in, out);
425 template <
typename ValueType,
typename Function>
429 auto complex_to_real = !(
430 is_complex<ValueType>() ||
433 if (complex_to_real) {
435 distributed::make_temporary_conversion<to_complex<ValueType>>(in);
437 distributed::make_temporary_conversion<to_complex<ValueType>>(out);
438 auto dense_alpha = gko::make_temporary_conversion<ValueType>(alpha);
443 fn(dense_alpha.get(),
444 dynamic_cast<const Vector*>(dense_in->create_real_view().get()),
445 dynamic_cast<Vector*>(dense_out->create_real_view().get()));
447 fn(gko::make_temporary_conversion<ValueType>(alpha).get(),
448 distributed::make_temporary_conversion<ValueType>(in).get(),
449 distributed::make_temporary_conversion<ValueType>(out).get());
457 template <
typename ValueType,
typename Function>
462 auto complex_to_real = !(
463 is_complex<ValueType>() ||
466 if (complex_to_real) {
468 distributed::make_temporary_conversion<to_complex<ValueType>>(in);
470 distributed::make_temporary_conversion<to_complex<ValueType>>(out);
471 auto dense_alpha = gko::make_temporary_conversion<ValueType>(alpha);
472 auto dense_beta = gko::make_temporary_conversion<ValueType>(beta);
477 fn(dense_alpha.get(),
478 dynamic_cast<const Vector*>(dense_in->create_real_view().get()),
480 dynamic_cast<Vector*>(dense_out->create_real_view().get()));
482 fn(gko::make_temporary_conversion<ValueType>(alpha).get(),
483 distributed::make_temporary_conversion<ValueType>(in).get(),
484 gko::make_temporary_conversion<ValueType>(beta).get(),
485 distributed::make_temporary_conversion<ValueType>(out).get());
506 template <
typename ValueType,
typename Function>
507 void precision_dispatch_real_complex_distributed(Function fn,
const LinOp* in,
510 if (dynamic_cast<const experimental::distributed::DistributedBase*>(in)) {
511 experimental::distributed::precision_dispatch_real_complex<ValueType>(
514 gko::precision_dispatch_real_complex<ValueType>(fn, in, out);
523 template <
typename ValueType,
typename Function>
524 void precision_dispatch_real_complex_distributed(Function fn,
526 const LinOp* in, LinOp* out)
528 if (dynamic_cast<const experimental::distributed::DistributedBase*>(in)) {
529 experimental::distributed::precision_dispatch_real_complex<ValueType>(
532 gko::precision_dispatch_real_complex<ValueType>(fn, alpha, in, out);
541 template <
typename ValueType,
typename Function>
542 void precision_dispatch_real_complex_distributed(Function fn,
545 const LinOp* beta, LinOp* out)
547 if (dynamic_cast<const experimental::distributed::DistributedBase*>(in)) {
548 experimental::distributed::precision_dispatch_real_complex<ValueType>(
549 fn, alpha, in, beta, out);
551 gko::precision_dispatch_real_complex<ValueType>(fn, alpha, in, beta,
570 template <
typename ValueType,
typename Function,
typename... Args>
571 void precision_dispatch_real_complex_distributed(Function fn, Args*... args)
573 precision_dispatch_real_complex<ValueType>(fn, args...);
584 #endif // GKO_PUBLIC_CORE_BASE_PRECISION_DISPATCH_HPP_