1//===----------------------------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9// UNSUPPORTED: c++03, c++11, c++14, c++17, c++20
10
11// <flat_map>
12
13// flat_map& operator=(flat_map&& c)
14// noexcept(
15// is_nothrow_move_assignable<key_container_type>::value &&
16// is_nothrow_move_assignable<mapped_container_type>::value &&
17// is_nothrow_copy_assignable<key_compare>::value);
18
19// This tests a conforming extension
20
21#include <flat_map>
22#include <functional>
23#include <memory_resource>
24#include <type_traits>
25#include <vector>
26
27#include "MoveOnly.h"
28#include "test_allocator.h"
29#include "test_macros.h"
30
31struct MoveSensitiveComp {
32 MoveSensitiveComp() noexcept(false) = default;
33 MoveSensitiveComp(const MoveSensitiveComp&) noexcept(false) = default;
34 MoveSensitiveComp(MoveSensitiveComp&& rhs) { rhs.is_moved_from_ = true; }
35 MoveSensitiveComp& operator=(const MoveSensitiveComp&) noexcept = default;
36 MoveSensitiveComp& operator=(MoveSensitiveComp&& rhs) {
37 rhs.is_moved_from_ = true;
38 return *this;
39 }
40 bool operator()(const auto&, const auto&) const { return false; }
41 bool is_moved_from_ = false;
42};
43
44struct MoveThrowsComp {
45 MoveThrowsComp(MoveThrowsComp&&) noexcept(false);
46 MoveThrowsComp(const MoveThrowsComp&) noexcept(true);
47 MoveThrowsComp& operator=(MoveThrowsComp&&) noexcept(false);
48 MoveThrowsComp& operator=(const MoveThrowsComp&) noexcept(true);
49 bool operator()(const auto&, const auto&) const;
50};
51
52int main(int, char**) {
53 {
54 using C = std::flat_map<int, int>;
55 LIBCPP_STATIC_ASSERT(std::is_nothrow_move_assignable_v<C>);
56 }
57 {
58 using C =
59 std::flat_map<MoveOnly,
60 int,
61 std::less<MoveOnly>,
62 std::vector<MoveOnly, test_allocator<MoveOnly>>,
63 std::vector<int, test_allocator<int>>>;
64 static_assert(!std::is_nothrow_move_assignable_v<C>);
65 }
66 {
67 using C =
68 std::flat_map<int,
69 MoveOnly,
70 std::less<int>,
71 std::vector<int, test_allocator<int>>,
72 std::vector<MoveOnly, test_allocator<MoveOnly>>>;
73 static_assert(!std::is_nothrow_move_assignable_v<C>);
74 }
75 {
76 using C =
77 std::flat_map<MoveOnly,
78 int,
79 std::less<MoveOnly>,
80 std::vector<MoveOnly, other_allocator<MoveOnly>>,
81 std::vector<int, other_allocator<int>>>;
82 LIBCPP_STATIC_ASSERT(std::is_nothrow_move_assignable_v<C>);
83 }
84 {
85 using C =
86 std::flat_map<int,
87 MoveOnly,
88 std::less<int>,
89 std::vector<int, other_allocator<int>>,
90 std::vector<MoveOnly, other_allocator<MoveOnly>>>;
91 LIBCPP_STATIC_ASSERT(std::is_nothrow_move_assignable_v<C>);
92 }
93 {
94 // Test with a comparator that throws on move-assignment.
95 using C = std::flat_map<int, int, MoveThrowsComp>;
96 LIBCPP_STATIC_ASSERT(!std::is_nothrow_move_assignable_v<C>);
97 }
98 {
99 // Test with a container that throws on move-assignment.
100 using C = std::flat_map<int, int, std::less<int>, std::pmr::vector<int>, std::vector<int>>;
101 static_assert(!std::is_nothrow_move_assignable_v<C>);
102 }
103 {
104 // Test with a container that throws on move-assignment.
105 using C = std::flat_map<int, int, std::less<int>, std::vector<int>, std::pmr::vector<int>>;
106 static_assert(!std::is_nothrow_move_assignable_v<C>);
107 }
108
109 return 0;
110}
111

source code of libcxx/test/std/containers/container.adaptors/flat.map/flat.map.cons/move_assign_noexcept.pass.cpp