I have the following code for generically wrapping Petsc objects in a unique_ptr
, but it doesn't quite work the way I'd expect from cppreference's documentation on template type deduction: https://en.cppreference.com/w/cpp/language/class_template_argument_deduction.
template <typename obj_type, typename... constructor_args>
using petsc_cons = PetscErrorCode (*)(constructor_args..., obj_type *);
template <typename obj_type> using petsc_destr = PetscErrorCode (*)(obj_type *);
template <typename obj_type, typename... constructor_args>
auto petsc_make_unique(petsc_cons<obj_type, constructor_args...> construct,
petsc_destr<obj_type> destroy, constructor_args... args) {
// allocation code...
}
class NLOptimizer {
public:
NLOptimizer(const size_t num_vars)
: tao_ctx(petsc_make_unique<Tao>(TaoCreate, TaoDestroy,
PETSC_COMM_SELF)) {}
This fails on g++:
autodiff_tao.hpp: In constructor ‘auto_diff::optimize_tao::NLOptimizer<expr_t>::NLOptimizer(expr_t, size_t)’:
autodiff_tao.hpp:45:62: error: no matching function for call to ‘petsc_make_unique<Tao>(PetscErrorCode (&)(MPI_Comm, _p_Tao**), PetscErrorCode (&)(_p_Tao**), MPI_Comm)’
45 | PETSC_COMM_SELF)) // ,
| ^
autodiff_tao.hpp:24:6: note: candidate: ‘template<class obj_type, class ... constructor_args> auto auto_diff::optimize_tao::petsc_make_unique(auto_diff::optimize_tao::petsc_cons<obj_type, constructor_args ...>, auto_diff::optimize_tao::petsc_destr<obj_type>, constructor_args ...)’
24 | auto petsc_make_unique(petsc_cons<obj_type, constructor_args...> construct,
| ^~~~~~~~~~~~~~~~~
autodiff_tao.hpp:24:6: note: template argument deduction/substitution failed:
autodiff_tao.hpp:45:62: note: mismatched types ‘_p_Tao*’ and ‘ompi_communicator_t’
45 | PETSC_COMM_SELF)) // ,
Clang is able to deduce the parameter pack types and compiles the code above. Is this a bug in g++, clang, or am I relying on undefined behaviour here?
I've attempted this compilation on multiple minor versions of clang 9 and g++ 9, and several less successful variations of the code above.
Aucun commentaire:
Enregistrer un commentaire