Почему глобальный оператор космического корабля не ведет себя так, как ожидалось? - PullRequest
0 голосов
/ 08 апреля 2020
#include <compare>
#include <forward_list>

template<typename T>
struct A
{
    std::forward_list<T> l;
};

template<typename T>
auto operator<=>(const A<T>& lhs, const A<T>& rhs)
{
    return lhs.l <=> rhs.l;
}

int main()
{
    std::forward_list<int>{} < std::forward_list<int>{}; // ok

    A<int>{} < A<int>{}; // error
}

Скомпилировано с clang++ -std=c++20 -stdlib=libc++ main.cpp и сообщениями об ошибках:

main.cpp:13:18: error: invalid operands to binary expression ('const std::forward_list<int>' and 'const std::forward_list<int>')
    return lhs.l <=> rhs.l;
           ~~~~~ ^   ~~~~~
main.cpp:20:14: note: in instantiation of function template specialization 'operator<=><int>' requested here
    A<int>{} < A<int>{}; // error

Почему оператор глобального космического корабля не ведет себя должным образом?

1 Ответ

3 голосов
/ 08 апреля 2020

Похоже, что libc ++ (или любая из стандартных библиотек) еще полностью не реализовали добавления в библиотеку операторов космического корабля.

См. здесь для libc ++ и здесь для скомпилированной таблицы на cppreference.com. Соответствующим документом, добавляющим operator<=> к std::forward_list, является P1614.

Если вы посмотрите исходный код libc ++ для std::forward_list здесь , вы увидите, что здесь нет упоминания operator<=> все же и другие вторичные операторы сравнения по-прежнему определены безоговорочно (что не должно быть в случае C ++ 20).

std::forward_list<int>{} < std::forward_list<int>{}; компилируется, поскольку использует operator<, а не operator<=>. Если вы попробуете std::forward_list<int>{} <=> std::forward_list<int>{} напрямую, это также приведет к сбою (в текущем состоянии libc ++).

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...