Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

redefine < operator to use in stl algorithms for strings

Is it possible to redefine operator < for strings without modifying std namespace, to make this operator use in standard algorithms? For example, I can write:

namespace std
{

    bool operator <(const std::string & rhs, const std::string & lhs)
    {
        std::cout << "lol";
        return false;
    }

}

int main()
{
    std::vector<std::string> lol = { "a", "b", "ba", "aa" };
    std::sort(lol.begin(), lol.end());
}

and "lol" will be printed several times. But if I move operator < outside from std namespace, default operator < will be used and nothing will be printed. Is it possible to make std::sort using custom operator < without including it to std namespace?

Yes I know, I can pass another comparator to std::sort but it's interesting for me if I could do what I asked and how?

Also am I correct, that it's correct to add such template specialization to std namespace?

Update: This is not practical question, I just want to know how can I do that if it's possible.

like image 979
Andrey Nekrasov Avatar asked Dec 10 '22 11:12

Andrey Nekrasov


2 Answers

No, it is not. Adding a function to the standard namespace is undefined behavior. [namespace.std]/1 states:

The behavior of a C++ program is undefined if it adds declarations or definitions to namespace std or to a namespace within namespace std unless otherwise specified. A program may add a template specialization for any standard library template to namespace std only if the declaration depends on a user-defined type and the specialization meets the standard library requirements for the original template and is not explicitly prohibited.

If you want to change how std::sort sorts then you can provide a lambda and define what you want

std::sort(std::begin(foo), std::end(foo), [](const auto& lhs, const auto& rhs) { /* your code here */ });
like image 125
NathanOliver Avatar answered Jan 12 '23 09:01

NathanOliver


Is it possible to redefine operator < for strings without modifiying std namespace

You can define the overload in another namespace, sure. But as you have found out, it will not be found by overload resolution unless explicitly qualified.

Is it possible to make std::sort using custom operator < without including it to std namespace?

Yes, and you already seem to know how:

Yes I know, I can pass another comparator to std::sort

This is exactly what the comparator argument is for.

Also am I correct, that it's corect to add such template specialization to std namespace?

That is not a template specialization; It is a function definition and you may not add function definitions to std namespace - or else the behaviour is undefined. You would be allowed to add template specializations, but only if at least one type argument is a user defined type.

like image 25
eerorika Avatar answered Jan 12 '23 10:01

eerorika