TiledArray  0.7.0
cast.h
Go to the documentation of this file.
1 /*
2  * This file is a part of TiledArray.
3  * Copyright (C) 2016 Virginia Tech
4  *
5  * This program is free software: you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation, either version 3 of the License, or
8  * (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program. If not, see <http://www.gnu.org/licenses/>.
17  *
18  * Justus Calvin
19  * Department of Chemistry, Virginia Tech
20  *
21  * cast.h
22  * Jan 10, 2016
23  *
24  */
25 
26 #ifndef TILEDARRAY_TILE_INTERFACE_CAST_H__INCLUDED
27 #define TILEDARRAY_TILE_INTERFACE_CAST_H__INCLUDED
28 
29 #include "../type_traits.h"
30 #include "../meta.h"
31 
32 namespace TiledArray {
33 
34  template <typename Result, typename Arg, typename Enabler = void> class Cast;
35 
36  namespace tile_interface {
37 
38  template <typename Result, typename Arg, typename Enabler>
39  class Cast;
40 
42 
50  template <typename Result, typename Arg>
51  class Cast<Result, Arg,
52  std::enable_if_t<detail::has_conversion_operator<
53  Arg, madness::Future<Result>>::value ||
54  detail::is_convertible<Arg, Result>::value>
55  > {
56 
57  public:
58 
59  typedef Result result_type;
60  typedef Arg argument_type;
61  static const constexpr bool is_nonblocking =
63  madness::Future<result_type>>::value;
64 
65  // basic type sanity checks
66  static_assert(
67  std::is_same<result_type, std::decay_t<result_type>>::value,
68  "Cast<Result,Arg>: Result must be a non-const non-ref type");
69  static_assert(
70  std::is_same<argument_type, std::decay_t<argument_type>>::value,
71  "Cast<Result,Arg>: Arg must be a non-const non-ref type");
72  static_assert(
74  argument_type, madness::Future<result_type>>::value ||
76  "Cast<Result,Arg> does not know how to construct Result or "
77  "Future<Result> from Arg");
78 
79  private:
80  template <typename Result_, typename Arg_,
81  typename = std::enable_if_t<detail::is_convertible<
82  std::decay_t<Arg_>, Result_>::value>>
83  static auto invoker(Arg_&& arg) {
84  auto exec = [](Arg_&& arg) {
85  return static_cast<Result_>(std::forward<Arg_>(arg));
86  };
87  return TiledArray::meta::invoke(exec, arg);
88  }
89  template <typename Result_, typename Arg_>
90  static auto invoker(
91  Arg_&& arg,
92  std::enable_if_t<detail::has_conversion_operator<
93  std::decay_t<Arg_>, madness::Future<Result_>>::value>* =
94  nullptr) {
95  auto exec = [](Arg_&& arg) {
96  return static_cast<madness::Future<Result_>>(std::forward<Arg_>(arg));
97  };
98  return TiledArray::meta::invoke(exec, std::forward<Arg_>(arg));
99  }
100 
101  public:
102 
105  template <typename Arg_, typename = std::enable_if_t<std::is_same<
106  argument_type, std::decay_t<Arg_>>::value>>
107  auto operator()(Arg_&& arg) const {
108  return this->invoker<result_type>(arg);
109  }
110 
111  }; // class Cast
112 
114 
122  template <typename Result, typename Arg>
123  class Cast<Result, Arg,
124  typename std::enable_if<
125  is_lazy_tile<Arg>::value &&
126  ! std::is_same<Result, typename TiledArray::eval_trait<Arg>::type>::value
127  >::type>
128  {
129  private:
130  typedef typename TiledArray::eval_trait<Arg>::type
131  eval_type;
136  public:
137 
138  typedef Result result_type;
139  typedef Arg argument_type;
140 
142 
150  template <typename Arg_, typename = std::enable_if_t<std::is_same<
151  argument_type, std::decay_t<Arg_>>::value>>
152  auto operator()(Arg_&& arg) const {
153  arg_to_eval_caster_type cast_to_eval;
154  eval_to_result_caster_type cast_to_result;
156  return invoke(cast_to_result, invoke(cast_to_eval, arg));
157  }
158 
159  }; // class Cast
160 
161  } // namespace tile_interface
162 
163 
165 
170  template <typename Result, typename Arg, typename Enabler>
171  class Cast : public TiledArray::tile_interface::Cast<Result, Arg, Enabler> { };
172 
177  template <typename Arg, typename Result = typename TiledArray::eval_trait<std::decay_t<Arg>>::type>
178  auto invoke_cast(Arg&& arg) {
180  return TiledArray::meta::invoke(cast, std::forward<Arg>(arg));
181  }
182 
183 } // namespace TiledArray
184 
185 #endif // TILEDARRAY_TILE_INTERFACE_CAST_H__INCLUDED
Tile cast operation.
Definition: cast.h:34
auto invoke_cast(Arg &&arg)
Definition: cast.h:178
STL namespace.
auto invoke(Function &&fn, Args &&... args) -> typename std::enable_if< !or_reduce< false, madness::is_future< std::decay_t< Args >>::value... >::value, decltype(fn(args...))>::type
Definition: meta.h:52