我最近尝试研究libstdc++源代码(GCC 7.2),感到困惑。可能我错过了一些重要的事情,但是我开始认为不可能实现完全符合C++标准的 basic_string 类。

这是我面临的一个问题。

  • basic_string 应该能够接受自定义分配器类作为模板参数。
  • 分配方法是分配器的一部分。
  • 分配允许返回用户定义类型的对象,该对象的作用类似于指向已分配数据的指针。我们称之为 my_pointer
  • my_pointer 应该仅满足 NullablePointer RandomAccessIterator 的要求。所有其他要求都是可选的。根据标准,我们可能无法将 my_pointer 转换为 CharT * 类型(另一个 basic_string 模板参数),因为它是可选的。
  • 另一方面, const CharT * c_str()方法应作为标准的一部分实现,因此我们必须知道如何进行此转换。

  • 项目4和5冲突,我不知道如何解决。
    希望你能帮助我弄清楚。

    谢谢!

    最佳答案

    该标准有几项要求,始终共同确保至少可以间接进行转换

  • 给定basic_­string<charT, traits, Allocator>the standard requires charTallocator_traits<Allocator>::value_type相等。
  • allocator_traits<Allocator>::pointer is required可以是Allocator::pointerAllocator::value_type*
  • 在前一种情况下,给定Allocator::pointer p*p is requiredAllocator::value_type&
  • 在后一种情况下,一切都是微不足道的。
  • Allocator::pointer is requiredcontiguous iterator,这需要给定一个连续的迭代器q*(q + n) == *(addressof(*q) + n)
  • 给定Allocator aa.allocate(n) is required返回Allocator::pointer

  • 将所有内容组合在一起,这意味着这始终是正确的
    template<typename charT, typename traits = /* ... */, typename Allocator = /* ... */>
    class basic_string
    {
        typename std::allocator_traits<Allocator>::pointer _data;
        // ...
    
    public:
        charT* c_str() { return std::addressof(*_data); }
        // ...
    };
    
    _data可能存储先前调用Allocator::allocate的结果的位置

    10-08 11:53