![]() |
Home | Libraries | People | FAQ | More |
Copyright © 2012 Marshall Clow
Copyright © 2015 Beman Dawes
Distributed under the Boost Software License, Version 1.0. http://www.boost.org/LICENSE_1_0.txt
Table of Contents
Boost.StringView is an implementation of string_view
as specified in N4480:
ISO/IEC DTS 19568, Technical Specification - C++ Extensions for Library Fundamentals.
When you are parsing/processing strings from some external source, frequently
you want to pass a piece of text to a procedure for specialized processing.
The canonical way to do this is as a std::string
,
but that has certain drawbacks:
1) If you are processing a buffer of text (say a HTTP response or the contents of a file), then you have to create the string from the text you want to pass, which involves memory allocation and copying of data.
2) if a routine receives a constant std::string
and wants to pass a portion of that string to another routine, then it must
create a new string of that substring.
3) A routine receives a constant std::string
and wants to return a portion of the string, then it must create a new string
to return.
string_view
is designed to
solve these efficiency problems. A string_view
is a read-only reference to a contiguous sequence of characters, and provides
much of the functionality of std::string
.
A string_view
is cheap to create,
copy and pass by value, because it does not actually own the storage that it
points to.
A string_view
is implemented
as a small struct that contains a pointer to the start of the character data
and a count. A string_view
is cheap to create and cheap to copy.
string_view
acts as a container;
it includes all the methods that you would expect in a container, including
iteration support, operator []
,
at
and size
.
It can be used with any of the iterator-based algorithms in the STL - as long
as you don't need to change the underlying data (sort
and remove
, for example, will
not work)
Besides generic container functionality, string_view
provides a subset of the interface of std::string
.
This makes it easy to replace parameters of type const
std::string &
with boost::string_view
. Like std::string
,
string_view
has a static member
variable named npos
to denote
the result of failed searches, and to mean "the end".
Because a string_view
does
not own the data that it "points to", it introduces lifetime issues
into code that uses it. The programmer must ensure that the data that a string_view
refers to exists as long as the
string_view
does.
Note: The header actually contains a class template, basic_string_view
and four typedefs:
template<class charT, class traits = char_traits<charT>> class basic_string_view; typedef basic_string_view<char> string_view; typedef basic_string_view<char16_t> u16string_view; typedef basic_string_view<char32_t> u32string_view; typedef basic_string_view<wchar_t> wstring_view;
So you can have views of strings of any of the four built-in character types
as well as strings of user-defined character-like type strings. For the sake
of simple exposition, we concentrate on string_view
(i.e. char
strings) in this documentation.
Integrating string_view
into
your code is fairly simple. Wherever you pass a const
std::string &
or std::string
as a parameter, that's a candidate
for passing a boost::string_view
.
std::string extract_part ( const std::string &bar ) { return bar.substr ( 2, 3 ); } if ( extract_part ( "ABCDEFG" ).front() == 'C' ) { /* do something */ }
Let's figure out what happens in this (contrived) example.
First, a temporary string is created from the string literal "ABCDEFG"
, and it is passed (by reference)
to the routine extract_part
.
Then a second string is created in the call std::string::substr
and returned to extract_part
(this copy may be elided by RVO). Then extract_part
returns that string back to the caller (again this copy may be elided). The
first temporary string is deallocated, and front
is called on the second string, and then it is deallocated as well.
Two std::string
s are created, and two copy operations.
That's (potentially) four memory allocations and deallocations, and the associated
copying of data.
Now let's look at the same code with string_view
:
boost::string_view extract_part ( boost::string_view bar ) { return bar.substr ( 2, 3 ); } if ( extract_part ( "ABCDEFG" ).front() == "C" ) { /* do something */ }
No memory allocations. No copying of character data. No changes to the code
other than the types. There are two string_view
s
created, and two string_view
s
copied, but those are cheap operations.
The header file "string_view.hpp" defines a class template boost::basic_string_view
,
and four specializations - for char
/ wchar_t
/ char16_t
/ char32_t
.
#include <boost/utility/string_view.hpp>
Types:
typedef traits traits_type; typedef charT value_type; typedef charT* pointer; typedef const charT* const_pointer; typedef charT& reference; typedef const charT& const_reference; typedef const_pointer const_iterator; // implementation defined typedef const_iterator iterator; typedef std::reverse_iterator<const_iterator> const_reverse_iterator; typedef const_reverse_iterator reverse_iterator; typedef std::size_t size_type; typedef std::ptrdiff_t difference_type; static BOOST_CONSTEXPR_OR_CONST size_type npos = size_type(-1);
Construction and copying:
BOOST_CONSTEXPR basic_string_view () BOOST_NOEXCEPT; // Constructs empty string_view BOOST_CONSTEXPR basic_string_view (const basic_string_view &rhs) BOOST_NOEXCEPT; basic_string_view& operator=(const basic_string_view &rhs) BOOST_NOEXCEPT; template<typename Allocator> basic_string_view(const std::basic_string<charT, traits, Allocator>& str) BOOST_NOEXCEPT; // Ctor from std::string BOOST_CONSTEXPR basic_string_view(const charT* str); // Ctor from NULL-terminated string BOOST_CONSTEXPR basic_string_view(const charT* str, size_type len); // Ctor from pointer, length pair
string_view
does not define
a move constructor or a move-assignment operator because copying a string_view
is just as cheap as moving one
would be.
Basic container-like functions:
BOOST_CONSTEXPR size_type size() const BOOST_NOEXCEPT ; BOOST_CONSTEXPR size_type length() const BOOST_NOEXCEPT ; BOOST_CONSTEXPR size_type max_size() const BOOST_NOEXCEPT ; BOOST_CONSTEXPR bool empty() const BOOST_NOEXCEPT ; // All iterators are const_iterators BOOST_CONSTEXPR const_iterator begin() const BOOST_NOEXCEPT ; BOOST_CONSTEXPR const_iterator cbegin() const BOOST_NOEXCEPT ; BOOST_CONSTEXPR const_iterator end() const BOOST_NOEXCEPT ; BOOST_CONSTEXPR const_iterator cend() const BOOST_NOEXCEPT ; const_reverse_iterator rbegin() const BOOST_NOEXCEPT ; const_reverse_iterator crbegin() const BOOST_NOEXCEPT ; const_reverse_iterator rend() const BOOST_NOEXCEPT ; const_reverse_iterator crend() const BOOST_NOEXCEPT ;
Access to the individual elements (all of which are const):
BOOST_CONSTEXPR const charT& operator[](size_type pos) const ; BOOST_CONSTEXPR const charT& at(size_t pos) const ; BOOST_CONSTEXPR const charT& front() const ; BOOST_CONSTEXPR const charT& back() const ; BOOST_CONSTEXPR const charT* data() const BOOST_NOEXCEPT ;
Modifying the string_view
(but
not the underlying data):
void clear(); // boost extension BOOST_CXX14_CONSTEXPR void remove_prefix(size_type n); BOOST_CXX14_CONSTEXPR void remove_suffix(size_type n); BOOST_CXX14_CONSTEXPR void swap(basic_string_view& s) BOOST_NOEXCEPT;
Searching:
BOOST_CXX14_CONSTEXPR size_type find(basic_string_view s, size_type pos = 0) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find(charT c, size_type pos = 0) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find(const charT* s, size_type pos, size_type n) const; BOOST_CXX14_CONSTEXPR size_type find(const charT* s, size_type pos = 0) const; BOOST_CXX14_CONSTEXPR size_type rfind(basic_string_view s, size_type pos = npos) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type rfind(charT c, size_type pos = npos) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type rfind(const charT* s, size_type pos, size_type n) const; BOOST_CXX14_CONSTEXPR size_type rfind(const charT* s, size_type pos = npos) const; BOOST_CXX14_CONSTEXPR size_type find_first_of(basic_string_view s, size_type pos = 0) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find_first_of(charT c, size_type pos = 0) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find_first_of(const charT* s, size_type pos, size_type n) const; BOOST_CXX14_CONSTEXPR size_type find_first_of(const charT* s, size_type pos = 0) const; BOOST_CXX14_CONSTEXPR size_type find_last_of(basic_string_view s, size_type pos = npos) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find_last_of(charT c, size_type pos = npos) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find_last_of(const charT* s, size_type pos, size_type n) const; BOOST_CXX14_CONSTEXPR size_type find_last_of(const charT* s, size_type pos = npos) const; BOOST_CXX14_CONSTEXPR size_type find_first_not_of(basic_string_view s, size_type pos = 0) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find_first_not_of(charT c, size_type pos = 0) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find_first_not_of(const charT* s, size_type pos, size_type n) const; BOOST_CXX14_CONSTEXPR size_type find_first_not_of(const charT* s, size_type pos = 0) const; BOOST_CXX14_CONSTEXPR size_type find_last_not_of(basic_string_view s, size_type pos = npos) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find_last_not_of(charT c, size_type pos = npos) const BOOST_NOEXCEPT; BOOST_CXX14_CONSTEXPR size_type find_last_not_of(const charT* s, size_type pos, size_type n) const; BOOST_CXX14_CONSTEXPR size_type find_last_not_of(const charT* s, size_type pos = npos) const; BOOST_CONSTEXPR bool starts_with(charT c) const ; // boost extension BOOST_CONSTEXPR bool starts_with(basic_string_view x) const ; // boost extension BOOST_CONSTEXPR bool ends_with(charT c) const ; // boost extension BOOST_CONSTEXPR bool ends_with(basic_string_view x) const ; // boost extension
String-like operations:
template<class Allocator> // Only present if compiler supports C++11 explicit conversion explicit operator basic_string<charT, traits, Allocator>() const; template<class Allocator = allocator<charT> > // Default only present if compiler supports basic_string<charT, traits, Allocator> // C++11 default template parameters to_string(const Allocator& a = Allocator()) const; size_type copy(charT* s, size_type n, size_type pos = 0) const; BOOST_CXX14_CONSTEXPR basic_string_view substr(size_type pos, size_type n=npos) const ; // Create new string_view
Comparison:
To be supplied
This Boost implementation only requires a C++03 compliant compiler.
The actual Library Fundamentals specification assumes a C++14 compliant compiler, so a few features are only present if actually supported by the compiler. Boost macros such as BOOST_CONSTEXPR, BOOST_CXX14_CONSTEXPR, and BOOST_NOEXCEPT supply certain features if supported by the compiler.
Last revised: July 17, 2015 at 19:19:23 GMT |