select_on_container_copy_construction не вызывается для std :: string - PullRequest
0 голосов
/ 19 декабря 2018

select_on_container_copy_construction в моем распределителе не вызывается для std:::string.Он отлично работает при использовании с vector жестким.Почему поведение отличается?Это ошибка в GCC?

Я использую gcc версии 5.4.0.

Пример кода с минимальным распределителем:

#include <iostream>
#include <vector>

template<class T>
class allocator {
public:
  typedef T value_type;

  using propagate_on_container_copy_assignment = std::true_type; // for consistency
  using propagate_on_container_move_assignment = std::true_type; // to avoid the pessimization
  using propagate_on_container_swap = std::true_type; // to avoid the undefined behavior

  allocator<T> select_on_container_copy_construction() const {
    throw std::bad_alloc();
  }

  T *allocate(const std::size_t n) {
    return static_cast<T *>(::operator new(n * sizeof(T)));
  }

  void deallocate(T *, const std::size_t) { }
};

template< class T1, class T2 >
bool operator==(const allocator<T1>&, const allocator<T2>&) noexcept {
  return true;
}

template< class T1, class T2 >
bool operator!=(const allocator<T1>&, const allocator<T2>&) noexcept {
  return false;
}

int main()
{
  try {
    std::basic_string<char, std::char_traits<char>, allocator<char>> s;
    auto ss = s;
  } catch (std::bad_alloc const&) {
    std::cout << "string worked\n";
  }

  try {
    std::vector<int, allocator<int>> v;
    auto vv = v;
  } catch (std::bad_alloc const&) {
    std::cout << "vector worked\n";
  }
}

Программа должна напечатать оба "строка сработала »и« вектор сработал », но он печатает только последний.

1 Ответ

0 голосов
/ 19 декабря 2018

Это ошибка в libstdc ++, которая была устранена в выпуске 6.1 этим PR .

Конкретное соответствующее изменение было от:

basic_string(const basic_string& __str)
: _M_dataplus(_M_local_data(), __str._M_get_allocator()) // TODO A traits

до:

basic_string(const basic_string& __str)
: _M_dataplus(_M_local_data(),
    _Alloc_traits::_S_select_on_copy(__str._M_get_allocator()))

Я не уверен, было ли открытое сообщение об ошибке.Я не могу найти его, и сообщение о коммите не ссылается на него.

...