Как может я использовать станд.:: карты с пользовательскими типами как ключ?

Я задаюсь вопросом, почему я не могу использовать карты STL с пользовательскими классами. Когда я компилирую код ниже, я получаю следующее загадочное сообщение об ошибке.Что это значит? Кроме того, почему это только происходит с пользовательскими типами? (Типы примитивов хорошо, когда они используются в качестве ключа.)

C:\MinGW\bin..\lib\gcc\mingw32\3.4.5........\include\c ++\3.4.5\bits\stl_function.h || В функции членства 'bool станд.:: меньше <_Tp>:: оператор () (константа _Tp&, константа _Tp&) константа [с _Tp = Class1] ':|

C:\MinGW\bin..\lib\gcc\mingw32\3.4.5........\include\c ++\3.4.5\bits\stl_map.h|338|instantiated от '_Tp& станд.:: карта <_Key, _Tp, _Compare, _Alloc>:: оператор [] (константа _Key&) [с _Key = Class1, _Tp = интервал, _Compare = станд.:: меньше, _Alloc = станд.:: средство выделения>]' |

C:\Users\Admin\Documents\dev\sandbox\sandbox\sandbox.cpp|24|instantiated отсюда |

C:\MinGW\bin..\lib\gcc\mingw32\3.4.5........\include\c ++\3.4.5\bits\stl_function.h|227|error: никакое соответствие для 'оператора <' в '__ x <__ y' | || === законченная Сборка: 1 ошибка, 0 предупреждений === |

#include <iostream>
#include <map>

using namespace std;

class Class1
{
public:
    Class1(int id);

private:
    int id;
};

Class1::Class1(int id): id(id)
{}

int main()
{
    Class1 c1(1);

    map< Class1 , int> c2int;
    c2int[c1] = 12;

    return 0;
}
59
задан honk 16 September 2019 в 12:17
поделиться

4 ответа

Вам необходимо определить operator < для Class1.

Карта должна сравнивать значения с помощью operator <и, следовательно, вам необходимо предоставить то же самое, когда пользовательский класс используется в качестве ключа.

class Class1
{
public:
    Class1(int id);

    bool operator <(const Class1& rhs) const
    {
        return id < rhs.id;
    }
private:
    int id;
};
14
ответ дан 24 November 2019 в 18:02
поделиться

На самом деле у вас нет , чтобы определить operator < для вашего класса. Вы также можете создать для него класс объекта функции компаратора и использовать его для специализации std :: map . Чтобы расширить ваш пример:

struct Class1Compare
{
   bool operator() (const Class1& lhs, const Class1& rhs) const
   {
       return lhs.id < rhs.id;
   }
};

std::map<Class1, int, Class1Compare> c2int;

Так получилось, что значение по умолчанию для третьего параметра шаблона std :: map - std :: less , который будет делегирован operator <, определенный для вашего класса (и завершается ошибкой, если его нет). Но иногда вы хотите, чтобы объекты можно было использовать в качестве ключей карты, но на самом деле у вас нет никакой осмысленной семантики сравнения, и поэтому вы не хотите вводить людей в заблуждение, предоставляя operator < в ваш класс только для этого. Если это так, вы можете использовать описанный выше трюк.

132
ответ дан 24 November 2019 в 18:02
поделиться

По умолчанию std :: map std :: set ) используйте operator < для определения сортировки. Следовательно, вам необходимо определить operator < в вашем классе.

Два объекта считаются эквивалентными if! (A .

Если по какой-либо причине вы хотите использовать другой компаратор, можно изменить третий аргумент шаблона карты ,

23
ответ дан 24 November 2019 в 18:02
поделиться

Ключи должны быть сопоставимы, но вы не определили подходящий оператор < для своего пользовательского класса.

3
ответ дан 24 November 2019 в 18:02
поделиться
Другие вопросы по тегам:

Похожие вопросы: