Is it legal in C++ to specialize std::minus for user-defined types?

Viewed 107

Does the standard library permit users to specialize function objects like std::plus and std::minus for custom types?

If the answer to my first question is yes, are users allowed to change the declaration of the call operator? For example, since C++14 std::minus::operator() is declared as follows:

constexpr T operator()( const T& lhs, const T& rhs ) const;

Would it be legal to change this operator such that it is no longer constexpr or returns double instead of T?

namespace std
{
    template <> 
    struct minus<MyArrayType>
    {
        double operator ()(const MyArrayType& x, const MyArrayType& y) const
        {
            return l2_norm(x - y);
        }
    };
}   // std
1 Answers

The rules for extending namespace std says:

It is allowed to add template specializations for any standard library class template to the namespace std only if the declaration depends on at least one program-defined type and the specialization satisfies all requirements for the original template, except where such specializations are prohibited.

(emphasis mine)

So in your case, adding a specialization for the program-defined type MyArrayType would work.

However, the return type of the member operator() must be MyArrayType, not double. Also, the member operator() must be constexpr.

Violating either of these means the specialization doesn't satisfy the requirements of the primary template.

Related