Spec-Zone.ru › C++

std::unordered_map<Key,T,Hash,KeyEqual,Allocator>::try_emplace

template< class... Args >
std::pair<iterator, bool> try_emplace( const Key& k, Args&&... args );
(1) (since C++17)
template< class... Args >
std::pair<iterator, bool> try_emplace( Key&& k, Args&&... args );
(2) (since C++17)
template< class... Args >
iterator try_emplace( const_iterator hint, const Key& k, Args&&... args );
(3) (since C++17)
template< class... Args >
iterator try_emplace( const_iterator hint, Key&& k, Args&&... args );
(4) (since C++17)

Вставляет новый элемент в контейнер с ключом k и значением, сконструированным с помощью args, если в контейнере нет элемента с таким ключом.

1) Если ключ, эквивалентный k, уже существует в контейнере, ничего не делает. В противном случае ведет себя как emplace, за исключением того, что элемент конструируется как
value_type(std::piecewise_construct,

std::forward_as_tuple(k),
std::forward_as_tuple

(std::forward<Args>(args)...))
2) Если ключ, эквивалентный k, уже существует в контейнере, ничего не делает. В противном случае ведет себя как emplace, за исключением того, что элемент конструируется как
value_type(std::piecewise_construct,

std::forward_as_tuple(std::move(k)),
std::forward_as_tuple

(std::forward<Args>(args)...))
3) Если ключ, эквивалентный k, уже существует в контейнере, ничего не делает. В противном случае ведет себя как emplace_hint, за исключением того, что элемент конструируется как
value_type(std::piecewise_construct,

std::forward_as_tuple(k),
std::forward_as_tuple

(std::forward<Args>(args)...))
4) Если ключ, эквивалентный k, уже существует в контейнере, ничего не делает. В противном случае ведет себя как emplace_hint, за исключением того, что элемент конструируется как
value_type(std::piecewise_construct,

std::forward_as_tuple(std::move(k)),
std::forward_as_tuple

(std::forward<Args>(args)...))

Если после операции новое количество элементов больше старого max_load_factor() * bucket_count(), происходит перехеширование.
Если перехеширование происходит (из-за вставки), все итераторы становятся недействительными. В противном случае (без перехеширования) итераторы не становятся недействительными.

Параметры

k - ключ, используемый как для поиска, так и для вставки, если он не найден
hint - итератор на позицию перед которой будет вставлен новый элемент
args - аргументы, передаваемые конструктору элемента

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

1,2) То же, что и для emplace.
3,4) То же, что и для emplace_hint.

Сложность

1,2) То же, что и для emplace.
3,4) То же, что и для emplace_hint.

Примечания

В отличие от insert или emplace, эти функции не перемещают аргументы rvalue, если вставка не происходит, что облегчает манипулирование картами, значения которых являются типами с перемещением, такими как std::unordered_map<std::string, std::unique_ptr<foo>>. Кроме того, try_emplace обрабатывает ключ и аргументы в mapped_type отдельно, в отличие от emplace, которая требует аргументов для построения value_type (то есть, std::pair).

Макрокоманда проверки наличия функции Значение Std Функция
__cpp_lib_unordered_map_try_emplace 201411L (C++17) std::unordered_map::try_emplace,
std::unordered_map::insert_or_assign

Пример

#include <iostream>
#include <string>
#include <utility>
#include <unordered_map>
 
void print_node(const auto& node)
{
    std::cout << '[' << node.first << "] = " << node.second << '\n';
}
 
void print_result(auto const& pair)
{
    std::cout << (pair.second ? "inserted: " : "ignored:  ");
    print_node(*pair.first);
}
 
int main()
{
    using namespace std::literals;
    std::unordered_map<std::string, std::string> m;
 
    print_result(m.try_emplace("a", "a"s));
    print_result(m.try_emplace("b", "abcd"));
    print_result(m.try_emplace("c", 10, 'c'));
    print_result(m.try_emplace("c", "Won't be inserted"));
 
    for (const auto& p : m)
        print_node(p);
}

Возможный вывод:

inserted: [a] = a
inserted: [b] = abcd
inserted: [c] = cccccccccc
ignored:  [c] = cccccccccc
[a] = a
[b] = abcd
[c] = cccccccccc

См. также

emplace
создает элемент на месте
(публичный член-функция)
emplace_hint
создает элементы на месте с подсказкой
(публичный член-функция)
insert
вставляет элементы или узлы(since C++17)
(публичный член-функция)

© cppreference.com
Licensed under the Creative Commons Attribution-ShareAlike Unported License v3.0.
https://en.cppreference.com/w/cpp/container/unordered_map/try_emplace

Spec-Zone.ru

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