名稱空間
變體
操作

std::swap

來自 cppreference.com
< cpp‎ | 演算法
 
 
演算法庫
有約束演算法與針對範圍的演算法 (C++20)
有約束的演算法,例如 ranges::copyranges::sort 等……
執行策略 (C++17)
排序及相關操作
劃分操作
排序操作
二分搜尋操作
(於已劃分範圍上)
集合操作(於已排序範圍上)
歸併操作(於已排序範圍上)
堆操作
最小/最大值操作
(C++11)
(C++17)
字典序比較操作
排列操作
C 庫
數值操作
未初始化記憶體上的操作
 
定義於標頭檔案 <algorithm>
(C++11 前)
在標頭檔案 <utility> 中定義
(C++11 起)
定義於標頭檔案 <string_view>
template< class T >
void swap( T& a, T& b );
(1) (C++11 起有條件 noexcept)
(C++20 起為 constexpr)
template< class T2, std::size_t N >
void swap( T2 (&a)[N], T2 (&b)[N] );
(2) (C++11 起有條件 noexcept)
(C++20 起為 constexpr)

交換給定的值。

1) 交換 ab 的值。

僅若 std::is_move_constructible_v<T> && std::is_move_assignable_v<T>true 時,此過載才會參與過載決議。

(C++17 起)
2) 交換陣列 ab。等價於 std::swap_ranges(a, a + N, b)

僅若 std::is_swappable_v<T2>true 時,此過載才會參與過載決議。

(C++17 起)

目錄

[編輯] 引數

a, b - 要交換的值
型別要求
-
T 必須滿足 可複製構造 (CopyConstructible) 可複製賦值 (CopyAssignable) (C++11 前) 可移動構造 (MoveConstructible) 可移動賦值 (MoveAssignable) (C++11 起) 的要求。
-
T2 必須滿足 可交換 (Swappable) 的要求。

[編輯] 返回值

(無)

[編輯] 異常

1)

(無)

(C++11 前)
noexcept 規範:  
noexcept(

    std::is_nothrow_move_constructible<T>::value &&
    std::is_nothrow_move_assignable<T>::value

)
(C++11 起)
2)
noexcept 規範:  
noexcept(noexcept(swap(*a, *b)))
在異常說明中查詢識別符號 swap 時,除了按常規查詢規則找到的內容外,還會找到此函式模板,這使得異常說明等價於 C++17 的 std::is_nothrow_swappable
(C++11 起)
(C++17 前)
noexcept 規範:  
(C++17 起)

[編輯] 複雜度

1) 常數。
2)N 成線性。

[編輯] 特化

可以在名稱空間 std 中為程式定義型別特化 std::swap,但是 ADL 不會找到這種特化(名稱空間 std 不是程式定義型別的關聯名稱空間)。

(C++20 前)

使程式定義型別可交換的預期方法是,在該型別所在的名稱空間中提供一個非成員函式 swap:詳見可交換 (Swappable)

標準庫已經提供了以下過載

特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式模板) [編輯]
特化 std::swap 演算法
(函式) [編輯]
特化 std::swap 演算法
(函式) [編輯]
特化 std::swap 演算法
(函式) [編輯]
特化 std::swap 演算法
(函式) [編輯]
特化 std::swap 演算法
(函式) [編輯]
特化 std::swap 演算法
(函式) [編輯]

[編輯] 示例

#include <algorithm>
#include <iostream>
 
namespace Ns
{
    class A
    {
        int id {};
 
        friend void swap(A& lhs, A& rhs)
        {
            std::cout << "swap(" << lhs << ", " << rhs << ")\n";
            std::swap(lhs.id, rhs.id);
        }
 
        friend std::ostream& operator<<(std::ostream& os, A const& a)
        {
            return os << "A::id=" << a.id;
        }
 
    public:
        A(int i) : id {i} {}
        A(A const&) = delete;
        A& operator = (A const&) = delete;
    };
}
 
int main()
{
    int a = 5, b = 3;
    std::cout << a << ' ' << b << '\n';
    std::swap(a, b);
    std::cout << a << ' ' << b << '\n';
 
    Ns::A p {6}, q {9};
    std::cout << p << ' ' << q << '\n';
//  std::swap(p, q); // error, type requirements are not satisfied
    swap(p, q);      // OK, ADL finds the appropriate friend `swap`
    std::cout << p << ' ' << q << '\n';
}

輸出

5 3
3 5
A::id=6 A::id=9
swap(A::id=6, A::id=9)
A::id=9 A::id=6

[編輯] 缺陷報告

下列更改行為的缺陷報告追溯地應用於以前出版的 C++ 標準。

缺陷報告 應用於 釋出時的行為 正確的行為
LWG 227 C++98 T 未被要求為可複製構造的 (CopyConstructible) 可預設構造的 (DefaultConstructible)
(型別 T 的臨時物件可能無法構造)
T 也要求
可複製構造 (CopyConstructible)
LWG 809 C++98 陣列不能被交換 添加了過載 (2)
LWG 2554 C++11 交換多維陣列永遠不能
由於名稱查詢問題而為 noexcept
已修復

[編輯] 參閱

交換兩個物件的值
(自定義點物件)[編輯]
交換兩個迭代器所指向的元素
(函式模板) [編輯]
交換兩個範圍的元素
(函式模板) [編輯]
(C++14)
用新值替換引數並返回其舊值
(函式模板) [編輯]