- added basic_string allocator support to BasicStringRef, BasicCStringRef, BasicWriter::str, StringBuffer and BasicStringWriter

This commit is contained in:
Andrey Glebov 2016-12-22 15:24:26 +03:00
parent fac5546321
commit 240e9175bd
2 changed files with 42 additions and 23 deletions

View File

@ -440,7 +440,8 @@ class BasicFormatter;
/** /**
\rst \rst
A string reference. It can be constructed from a C string or ``std::string``. A string reference. It can be constructed from a C string or
``std::basic_string``.
You can use one of the following typedefs for common character types: You can use one of the following typedefs for common character types:
@ -483,19 +484,24 @@ class BasicStringRef {
/** /**
\rst \rst
Constructs a string reference from an ``std::string`` object. Constructs a string reference from a ``std::basic_string`` object.
\endrst \endrst
*/ */
BasicStringRef(const std::basic_string<Char> &s) template <typename Allocator>
BasicStringRef(
const std::basic_string<Char, std::char_traits<Char>, Allocator> &s)
: data_(s.c_str()), size_(s.size()) {} : data_(s.c_str()), size_(s.size()) {}
/** /**
\rst \rst
Converts a string reference to an ``std::string`` object. Converts a string reference to a ``std::basic_string`` object.
\endrst \endrst
*/ */
std::basic_string<Char> to_string() const { template <typename Allocator = std::allocator<Char> >
return std::basic_string<Char>(data_, size_); std::basic_string<Char, std::char_traits<Char>, Allocator>
to_string(const Allocator &allocator = Allocator()) const {
return std::basic_string<Char, std::char_traits<Char>, Allocator>(
data_, size_, allocator);
} }
/** Returns a pointer to the string data. */ /** Returns a pointer to the string data. */
@ -539,7 +545,7 @@ typedef BasicStringRef<wchar_t> WStringRef;
/** /**
\rst \rst
A reference to a null terminated string. It can be constructed from a C A reference to a null terminated string. It can be constructed from a C
string or ``std::string``. string or ``std::basic_string``.
You can use one of the following typedefs for common character types: You can use one of the following typedefs for common character types:
@ -572,10 +578,13 @@ class BasicCStringRef {
/** /**
\rst \rst
Constructs a string reference from an ``std::string`` object. Constructs a string reference from a ``std::basic_string`` object.
\endrst \endrst
*/ */
BasicCStringRef(const std::basic_string<Char> &s) : data_(s.c_str()) {} template <typename Allocator>
BasicCStringRef(
const std::basic_string<Char, std::char_traits<Char>, Allocator> &s)
: data_(s.c_str()) {}
/** Returns the pointer to a C string. */ /** Returns the pointer to a C string. */
const Char *c_str() const { return data_; } const Char *c_str() const { return data_; }
@ -2567,11 +2576,14 @@ class BasicWriter {
/** /**
\rst \rst
Returns the content of the output buffer as an `std::string`. Returns the content of the output buffer as a `std::basic_string`.
\endrst \endrst
*/ */
std::basic_string<Char> str() const { template <typename Allocator = std::allocator<Char> >
return std::basic_string<Char>(&buffer_[0], buffer_.size()); std::basic_string<Char, std::char_traits<Char>, Allocator> str(
const Allocator &allocator = Allocator()) const {
return std::basic_string<Char, std::char_traits<Char>, Allocator>(
&buffer_[0], buffer_.size(), allocator);
} }
/** /**

View File

@ -16,11 +16,14 @@ namespace fmt {
namespace internal { namespace internal {
// A buffer that stores data in ``std::string``. // A buffer that stores data in ``std::basic_string``.
template <typename Char> template <typename Char, typename Allocator = std::allocator<Char> >
class StringBuffer : public Buffer<Char> { class StringBuffer : public Buffer<Char> {
public:
typedef std::basic_string<Char, std::char_traits<Char>, Allocator> string_type;
private: private:
std::basic_string<Char> data_; string_type data_;
protected: protected:
virtual void grow(std::size_t size) FMT_OVERRIDE { virtual void grow(std::size_t size) FMT_OVERRIDE {
@ -30,8 +33,11 @@ class StringBuffer : public Buffer<Char> {
} }
public: public:
explicit StringBuffer(const Allocator &allocator = Allocator())
: data_(allocator) {}
// Moves the data to ``str`` clearing the buffer. // Moves the data to ``str`` clearing the buffer.
void move_to(std::basic_string<Char> &str) { void move_to(string_type &str) {
data_.resize(this->size_); data_.resize(this->size_);
str.swap(data_); str.swap(data_);
this->capacity_ = this->size_ = 0; this->capacity_ = this->size_ = 0;
@ -43,8 +49,8 @@ class StringBuffer : public Buffer<Char> {
/** /**
\rst \rst
This class template provides operations for formatting and writing data This class template provides operations for formatting and writing data
into a character stream. The output is stored in ``std::string`` that grows into a character stream. The output is stored in ``std::basic_string``
dynamically. that grows dynamically.
You can use one of the following typedefs for common character types You can use one of the following typedefs for common character types
and the standard allocator: and the standard allocator:
@ -68,13 +74,13 @@ class StringBuffer : public Buffer<Char> {
The answer is 42 The answer is 42
The output can be moved to an ``std::string`` with ``out.move_to()``. The output can be moved to a ``std::basic_string`` with ``out.move_to()``.
\endrst \endrst
*/ */
template <typename Char> template <typename Char, typename Allocator = std::allocator<Char> >
class BasicStringWriter : public BasicWriter<Char> { class BasicStringWriter : public BasicWriter<Char> {
private: private:
internal::StringBuffer<Char> buffer_; internal::StringBuffer<Char, Allocator> buffer_;
public: public:
/** /**
@ -82,14 +88,15 @@ class BasicStringWriter : public BasicWriter<Char> {
Constructs a :class:`fmt::BasicStringWriter` object. Constructs a :class:`fmt::BasicStringWriter` object.
\endrst \endrst
*/ */
BasicStringWriter() : BasicWriter<Char>(buffer_) {} explicit BasicStringWriter(const Allocator &allocator = Allocator())
: BasicWriter<Char>(buffer_), buffer_(allocator) {}
/** /**
\rst \rst
Moves the buffer content to *str* clearing the buffer. Moves the buffer content to *str* clearing the buffer.
\endrst \endrst
*/ */
void move_to(std::basic_string<Char> &str) { void move_to(std::basic_string<Char, std::char_traits<Char>, Allocator> &str) {
buffer_.move_to(str); buffer_.move_to(str);
} }
}; };