brintos

brintos / llvm-project-archived public Read only

0
0
Text · 6.0 KiB · a087704 Raw
184 lines · cpp
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-exception6//7//===----------------------------------------------------------------------===//8//9// UNSUPPORTED: c++03, c++11, c++1410 11// <map>12 13// class map14 15// template <class... Args>16//  pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);          // C++1717// template <class... Args>18//  pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);               // C++1719// template <class... Args>20//  iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args); // C++1721// template <class... Args>22//  iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);      // C++1723 24#include <map>25#include <cassert>26#include <iterator>27#include <tuple>28 29#include "test_macros.h"30 31class Moveable {32  Moveable(const Moveable&);33  Moveable& operator=(const Moveable&);34 35  int int_;36  double double_;37 38public:39  Moveable() : int_(0), double_(0) {}40  Moveable(int i, double d) : int_(i), double_(d) {}41  Moveable(Moveable&& x) : int_(x.int_), double_(x.double_) {42    x.int_    = -1;43    x.double_ = -1;44  }45  Moveable& operator=(Moveable&& x) {46    int_      = x.int_;47    x.int_    = -1;48    double_   = x.double_;49    x.double_ = -1;50    return *this;51  }52 53  bool operator==(const Moveable& x) const { return int_ == x.int_ && double_ == x.double_; }54  bool operator<(const Moveable& x) const { return int_ < x.int_ || (int_ == x.int_ && double_ < x.double_); }55 56  int get() const { return int_; }57  bool moved() const { return int_ == -1; }58};59 60int main(int, char**) {61  { // pair<iterator, bool> try_emplace(const key_type& k, Args&&... args);62    typedef std::map<int, Moveable> M;63    typedef std::pair<M::iterator, bool> R;64    M m;65    R r;66    for (int i = 0; i < 20; i += 2)67      m.emplace(i, Moveable(i, (double)i));68    assert(m.size() == 10);69 70    Moveable mv1(3, 3.0);71    for (int i = 0; i < 20; i += 2) {72      r = m.try_emplace(i, std::move(mv1));73      assert(m.size() == 10);74      assert(!r.second);           // was not inserted75      assert(!mv1.moved());        // was not moved from76      assert(r.first->first == i); // key77    }78 79    r = m.try_emplace(-1, std::move(mv1));80    assert(m.size() == 11);81    assert(r.second);                   // was inserted82    assert(mv1.moved());                // was moved from83    assert(r.first->first == -1);       // key84    assert(r.first->second.get() == 3); // value85 86    Moveable mv2(5, 3.0);87    r = m.try_emplace(5, std::move(mv2));88    assert(m.size() == 12);89    assert(r.second);                   // was inserted90    assert(mv2.moved());                // was moved from91    assert(r.first->first == 5);        // key92    assert(r.first->second.get() == 5); // value93 94    Moveable mv3(-1, 3.0);95    r = m.try_emplace(117, std::move(mv2));96    assert(m.size() == 13);97    assert(r.second);                    // was inserted98    assert(mv2.moved());                 // was moved from99    assert(r.first->first == 117);       // key100    assert(r.first->second.get() == -1); // value101  }102 103  { // pair<iterator, bool> try_emplace(key_type&& k, Args&&... args);104    typedef std::map<Moveable, Moveable> M;105    typedef std::pair<M::iterator, bool> R;106    M m;107    R r;108    for (int i = 0; i < 20; i += 2)109      m.emplace(Moveable(i, (double)i), Moveable(i + 1, (double)i + 1));110    assert(m.size() == 10);111 112    Moveable mvkey1(2, 2.0);113    Moveable mv1(4, 4.0);114    r = m.try_emplace(std::move(mvkey1), std::move(mv1));115    assert(m.size() == 10);116    assert(!r.second);                // was not inserted117    assert(!mv1.moved());             // was not moved from118    assert(!mvkey1.moved());          // was not moved from119    assert(r.first->first == mvkey1); // key120 121    Moveable mvkey2(3, 3.0);122    r = m.try_emplace(std::move(mvkey2), std::move(mv1));123    assert(m.size() == 11);124    assert(r.second);                   // was inserted125    assert(mv1.moved());                // was moved from126    assert(mvkey2.moved());             // was moved from127    assert(r.first->first.get() == 3);  // key128    assert(r.first->second.get() == 4); // value129  }130 131  { // iterator try_emplace(const_iterator hint, const key_type& k, Args&&... args);132    typedef std::map<int, Moveable> M;133    M m;134    M::iterator r;135    for (int i = 0; i < 20; i += 2)136      m.try_emplace(i, Moveable(i, (double)i));137    assert(m.size() == 10);138    M::const_iterator it = m.find(2);139 140    Moveable mv1(3, 3.0);141    for (int i = 0; i < 20; i += 2) {142      r = m.try_emplace(it, i, std::move(mv1));143      assert(m.size() == 10);144      assert(!mv1.moved());         // was not moved from145      assert(r->first == i);        // key146      assert(r->second.get() == i); // value147    }148 149    r = m.try_emplace(it, 3, std::move(mv1));150    assert(m.size() == 11);151    assert(mv1.moved());          // was moved from152    assert(r->first == 3);        // key153    assert(r->second.get() == 3); // value154  }155 156  { // iterator try_emplace(const_iterator hint, key_type&& k, Args&&... args);157    typedef std::map<Moveable, Moveable> M;158    M m;159    M::iterator r;160    for (int i = 0; i < 20; i += 2)161      m.emplace(Moveable(i, (double)i), Moveable(i + 1, (double)i + 1));162    assert(m.size() == 10);163    M::const_iterator it = std::next(m.cbegin());164 165    Moveable mvkey1(2, 2.0);166    Moveable mv1(4, 4.0);167    r = m.try_emplace(it, std::move(mvkey1), std::move(mv1));168    assert(m.size() == 10);169    assert(!mv1.moved());       // was not moved from170    assert(!mvkey1.moved());    // was not moved from171    assert(r->first == mvkey1); // key172 173    Moveable mvkey2(3, 3.0);174    r = m.try_emplace(it, std::move(mvkey2), std::move(mv1));175    assert(m.size() == 11);176    assert(mv1.moved());          // was moved from177    assert(mvkey2.moved());       // was moved from178    assert(r->first.get() == 3);  // key179    assert(r->second.get() == 4); // value180  }181 182  return 0;183}184