I find it rather convenient to have a class which basically acts like std::array but is indexed by values of some enum. I guess it's not very hard to imagine how to implement it, let's say it has a signature like this:
class enum_array <typename EnumT, typename ValueT, size_t N>
On the other hand while trying to implement all of the standard std::array concerned functions I've noticed that writing overloaded std::get function for such class template is not that easy.
First of all, I think that it's only natural for this std::get to have value of aforementioned enum as a template argument and because of it the most of the problems emerge:
1) If I want to define such function outside the class I have to do something like:
namespace std { template <EnumT Index, typename EnumT, typename ValueT, size_t N> EnumT &get (enum_array<EnumT, ValueT, N> &val)
But then the problem arouses that EnumT is still unknown while specifying the first template argument so this template is actually ill formed
If I put EnumT Index on the second or further place of argument list, then there's problem that I cannot really specify only this argument and will have to specify something else along with it and that will not look like normal std::get call on std::array.
2) If I define get function inside enum_array class as a friend function everything will be seemingly fine except the fact that then it'll be placed in the same namespace the class enum_array belongs to. And putting it in namespace std is not the best design.
So my question is: Can std::get with enum arguments be overloaded in a way that I mentioned for such class using C++ template mechanism?
(Want to point out that this question aroused mostly out of curiousity, afterall std::get is not the most useful function for std::array in my opinion)
template<auto Value>(a template non-type parameter whose type is deduced). So, you either have to specify one function (template) per enum type, à latemplate<first_enum Value> auto get(..);,template<second_enum Value> auto get(..);etc., or you have to (manually) pass the type of the enum value for each invocation, à laget<first_enum, Value0>(..);,get<second_enum, Value0>(..);