Spec-Zone.ru › C++

std::expected<T,E>::swap

constexpr void swap( expected& other ) noexcept(/*see below*/);
(с C++23)

Меняет содержимое с содержимым объекта other.

  • Если и this->has_value(), и other.has_value() истинны:
    • Если T является (возможно, с квалификатором cv) void, никаких изменений не происходит.
    • В противном случае, эквивалентно using std::swap; swap(*this, other);.
  • Если и this->has_value() и other.has_value() ложны, эквивалентно
    using std::swap; swap(this->error(), other.error());.
  • Если this->has_value() ложно, а other.has_value() истинно, вызывается other.swap(*this).
  • Если this->has_value() истинно, а other.has_value() ложно,
    • Если T является (возможно, с квалификатором cv) void, пусть unex обозначает член, представляющий неожиданное значение, эквивалентно:
std::construct_at(std::addressof(unex), std::move(other.unex));
std::destroy_at(std::addressof(other.unex));
  • В противном случае, пусть val обозначает член, представляющий ожидаемое значение, а unex обозначает член, представляющий неожиданное значение, эквивалентно:
if constexpr (std::is_nothrow_move_constructible_v<E>) {
    E temp(std::move(other.unex));
    std::destroy_at(std::addressof(other.unex));
    try {
        std::construct_at(std::addressof(other.val), std::move(val));
        std::destroy_at(std::addressof(val));
        std::construct_at(std::addressof(unex), std::move(temp));
    } catch(...) {
        std::construct_at(std::addressof(other.unex), std::move(temp));
        throw;
    }
} else {
    T temp(std::move(val));
    std::destroy_at(std::addressof(val));
    try {
        std::construct_at(std::addressof(unex), std::move(other.unex));
        std::destroy_at(std::addressof(other.unex));
        std::construct_at(std::addressof(other.val), std::move(temp));
    } catch(...) {
        std::construct_at(std::addressof(val), std::move(temp));
        throw;
    }
}
  • В любом случае, если исключение не было брошено, после swap, this->has_value() ложно, а other.has_value() истинно.

Эта функция участвует в разрешении перегрузки только если

  • либо T является (возможно, с квалификатором cv) void, или std::is_swappable_v<T> истинно, и
  • std::is_swappable_v<E> истинно, и
  • либо T является (возможно, с квалификатором cv) void, или std::is_move_constructible_v<T> истинно, и
  • std::is_move_constructible_v<E> истинно, и
  • по крайней мере одно из следующих истинно:
    • T является (возможно, с квалификатором cv) void
    • std::is_nothrow_move_constructible_v<T>
    • std::is_nothrow_move_constructible_v<E>

Параметры

other - объект, с которым нужно обменять содержимое

Возвращаемое значение

(нет)

Исключения

Если T является (возможно, с квалификатором cv) void,
noexcept спецификация:
noexcept(

std::is_nothrow_move_constructible_v<E> && std::is_nothrow_swappable_v<E>

)
В противном случае,
noexcept спецификация:
noexcept(

std::is_nothrow_move_constructible_v<T> && std::is_nothrow_swappable_v<T> &&
std::is_nothrow_move_constructible_v<E> && std::is_nothrow_swappable_v<E>

)

В случае брошенного исключения, состояние содержащихся значений *this и other определяется гарантией безопасности от исключений swap или T и E конструктора перемещения, который был вызван. Для обоих *this и other, если объект содержал ожидаемое значение, он останется содержащим ожидаемое значение, и наоборот.

Пример

См. также

swap(std::expected)
(C++23)
специализация алгоритма std::swap
(функция)

© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/w/cpp/utility/expected/swap

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API