1 #ifndef VERTEXCFD_UTILS_SMOOTHMIN_HPP
2 #define VERTEXCFD_UTILS_SMOOTHMIN_HPP
5 #include <Sacado_Fad_Exp_Expression.hpp>
6 #include <Sacado_Fad_Exp_ExpressionTraits.hpp>
7 #include <Sacado_mpl_disable_if.hpp>
8 #include <Sacado_mpl_enable_if.hpp>
24 template<
typename T1,
typename T2,
bool is_const_T2,
typename ExprSpec>
30 template<
typename T1,
typename T2>
31 class SmoothMinOp<T1, T2, false, Sacado::Fad::Exp::ExprSpecDefault>
32 :
public Expr<SmoothMinOp<T1, T2, false, Sacado::Fad::Exp::ExprSpecDefault>>
35 using ExprT1 =
typename std::remove_cv<T1>::type;
36 using ExprT2 =
typename std::remove_cv<T2>::type;
37 using value_type1 =
typename ExprT1::value_type;
38 using value_type2 =
typename ExprT2::value_type;
39 using value_type =
typename Sacado::Promote<value_type1, value_type2>::type;
40 using scalar_type1 =
typename ExprT1::scalar_type;
41 using scalar_type2 =
typename ExprT2::scalar_type;
43 typename Sacado::Promote<scalar_type1, scalar_type2>::type;
44 using expr_spec_type = Sacado::Fad::Exp::ExprSpecDefault;
46 SACADO_INLINE_FUNCTION
explicit SmoothMinOp(
const T1& x,
55 SACADO_INLINE_FUNCTION
int size()
const
57 const int sz1 = x_.size();
58 const int sz2 = y_.size();
59 return sz1 > sz2 ? sz1 : sz2;
62 SACADO_INLINE_FUNCTION
bool hasFastAccess()
const
64 return x_.hasFastAccess() && y_.hasFastAccess();
67 SACADO_INLINE_FUNCTION value_type val()
const
73 else if (x_ <= y_ - tol_)
80 * (x_.val() + y_.val()
82 * ((x_.val() - y_.val()) * (x_.val() - y_.val())
88 SACADO_INLINE_FUNCTION value_type dx(
int i)
const
94 else if (x_ <= y_ - tol_)
101 * (x_.dx(i) + y_.dx(i)
102 - (x_.val() - y_.val()) * (x_.dx(i) - y_.dx(i)) / tol_);
106 SACADO_INLINE_FUNCTION value_type fastAccessDx(
int i)
const
110 return y_.fastAccessDx(i);
112 else if (x_ <= y_ - tol_)
114 return x_.fastAccessDx(i);
119 * (x_.fastAccessDx(i) + y_.fastAccessDx(i)
120 - (x_.val() - y_.val())
121 * (x_.fastAccessDx(i) - y_.fastAccessDx(i)) / tol_);
132 template<
typename T1,
typename T2>
133 class SmoothMinOp<T1, T2, true, Sacado::Fad::Exp::ExprSpecDefault>
134 :
public Expr<SmoothMinOp<T1, T2, true, Sacado::Fad::Exp::ExprSpecDefault>>
137 using ExprT1 =
typename std::remove_cv<T1>::type;
139 using value_type =
typename ExprT1::value_type;
140 using scalar_type =
typename ExprT1::scalar_type;
141 using expr_spec_type = Sacado::Fad::Exp::ExprSpecDefault;
143 SACADO_INLINE_FUNCTION
explicit SmoothMinOp(
const T1& x,
152 SACADO_INLINE_FUNCTION
int size()
const {
return x_.size(); }
154 SACADO_INLINE_FUNCTION
bool hasFastAccess()
const
156 return x_.hasFastAccess();
159 SACADO_INLINE_FUNCTION value_type val()
const
165 else if (x_ <= c_ - tol_)
173 - 0.5 * ((x_.val() - c_) * (x_.val() - c_) / tol_ + tol_));
177 SACADO_INLINE_FUNCTION value_type dx(
int i)
const
183 else if (x_ <= c_ - tol_)
189 return 0.5 * (x_.dx(i) - (x_.val() - c_) * x_.dx(i) / tol_);
193 SACADO_INLINE_FUNCTION value_type fastAccessDx(
int i)
const
199 else if (x_ <= c_ - tol_)
201 return x_.fastAccessDx(i);
206 * (x_.fastAccessDx(i)
207 - (x_.val() - c_) * x_.fastAccessDx(i) / tol_);
219 SACADO_INLINE_FUNCTION
220 typename std::enable_if<std::is_trivial<T>::value, T>::type
221 min(
const T x,
const T y,
const double tol)
227 else if (x <= y - tol)
233 return 0.5 * (x + y - 0.5 * ((x - y) * (x - y) / tol + tol));
237 using Sacado::Fad::Exp::Expr;
238 using Sacado::Fad::Exp::ExprLevel;
239 using Sacado::Fad::Exp::IsFadExpr;
243 template<
typename T1,
typename T2>
244 SACADO_INLINE_FUNCTION
typename Sacado::mpl::enable_if_c<
245 IsFadExpr<T1>::value && IsFadExpr<T2>::value
246 && ExprLevel<T1>::value == ExprLevel<T2>::value,
247 SmoothMinOp<typename Expr<T1>::derived_type,
248 typename Expr<T2>::derived_type,
250 typename T1::expr_spec_type>>::type
251 min(
const T1& x,
const T2& y,
const double tol)
253 using expr_t = SmoothMinOp<typename Expr<T1>::derived_type,
254 typename Expr<T2>::derived_type,
256 typename T1::expr_spec_type>;
257 return expr_t(x.derived(), y.derived(), tol);
263 SACADO_INLINE_FUNCTION SmoothMinOp<typename Expr<T>::derived_type,
264 typename T::value_type,
266 typename T::expr_spec_type>
267 min(
const typename T::value_type& c,
const Expr<T>& y,
const double tol)
269 using ConstT =
typename T::value_type;
270 using expr_t = SmoothMinOp<typename Expr<T>::derived_type,
273 typename T::expr_spec_type>;
276 return expr_t(y.derived(), c, tol);
282 SACADO_INLINE_FUNCTION SmoothMinOp<typename Expr<T>::derived_type,
283 typename T::value_type,
285 typename T::expr_spec_type>
286 min(
const Expr<T>& x,
const typename T::value_type& c,
const double tol)
288 using ConstT =
typename T::value_type;
289 using expr_t = SmoothMinOp<typename Expr<T>::derived_type,
292 typename T::expr_spec_type>;
293 return expr_t(x.derived(), c, tol);
300 SACADO_INLINE_FUNCTION
typename Sacado::mpl::disable_if<
301 std::is_same<typename T::value_type, typename T::scalar_type>,
302 SmoothMinOp<typename Expr<T>::derived_type,
303 typename T::scalar_type,
305 typename T::expr_spec_type>>::type
306 min(
const typename T::scalar_type& c,
const Expr<T>& y,
const double tol)
308 using ConstT =
typename T::scalar_type;
309 using expr_t = SmoothMinOp<typename Expr<T>::derived_type,
312 typename T::expr_spec_type>;
315 return expr_t(y.derived(), c, tol);
322 SACADO_INLINE_FUNCTION
typename Sacado::mpl::disable_if<
323 std::is_same<typename T::value_type, typename T::scalar_type>,
324 SmoothMinOp<typename Expr<T>::derived_type,
325 typename T::scalar_type,
327 typename T::expr_spec_type>>::type
328 min(
const Expr<T>& x,
const typename T::scalar_type& c,
const double tol)
330 using ConstT =
typename T::scalar_type;
331 using expr_t = SmoothMinOp<typename Expr<T>::derived_type,
334 typename T::expr_spec_type>;
335 return expr_t(x.derived(), c, tol);
355 template<
typename T1,
typename T2,
bool c2,
typename E>
358 static constexpr
unsigned value_1 = ExprLevel<T1>::value;
359 static constexpr
unsigned value_2 = ExprLevel<T2>::value;
360 static constexpr
unsigned value = value_1 >= value_2 ? value_1 : value_2;
363 template<
typename T1,
typename T2,
bool c2,
typename E>
366 static const unsigned value =
true;
372 template<
typename T1,
typename T2,
bool c2,
typename E>
373 struct IsExpr<
VertexCFD::SmoothMath::SmoothMinOp<T1, T2, c2, E>>
375 static const unsigned value =
true;
378 template<
typename T1,
typename T2,
bool c2,
typename E>
379 struct BaseExprType<
VertexCFD::SmoothMath::SmoothMinOp<T1, T2, c2, E>>
381 using base_expr_1 =
typename BaseExprType<T1>::type;
382 using base_expr_2 =
typename BaseExprType<T2>::type;
383 using type =
typename Promote<base_expr_1, base_expr_2>::type;
386 template<
typename T1,
typename T2,
bool c2,
typename E>
387 struct IsSimdType<
VertexCFD::SmoothMath::SmoothMinOp<T1, T2, c2, E>>
389 static const bool value
390 = IsSimdType<
typename VertexCFD::SmoothMath::
391 SmoothMinOp<T1, T2, c2, E>::scalar_type>::value;
394 template<
typename T1,
typename T2,
bool c2,
typename E>
395 struct ValueType<
VertexCFD::SmoothMath::SmoothMinOp<T1, T2, c2, E>>
401 template<
typename T1,
typename T2,
bool c2,
typename E>
402 struct ScalarType<
VertexCFD::SmoothMath::SmoothMinOp<T1, T2, c2, E>>
410 #endif // end VERTEXCFD_UTILS_SMOOTHMIN_HPP