string_piece.h 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520
  1. // Copyright (c) 2012 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. // Copied from strings/stringpiece.h with modifications
  5. //
  6. // A string-like object that points to a sized piece of memory.
  7. //
  8. // You can use StringPiece as a function or method parameter. A StringPiece
  9. // parameter can receive a double-quoted string literal argument, a "const
  10. // char*" argument, a string argument, or a StringPiece argument with no data
  11. // copying. Systematic use of StringPiece for arguments reduces data
  12. // copies and strlen() calls.
  13. //
  14. // Prefer passing StringPieces by value:
  15. // void MyFunction(StringPiece arg);
  16. // If circumstances require, you may also pass by const reference:
  17. // void MyFunction(const StringPiece& arg); // not preferred
  18. // Both of these have the same lifetime semantics. Passing by value
  19. // generates slightly smaller code. For more discussion, Googlers can see
  20. // the thread go/stringpiecebyvalue on c-users.
  21. #ifndef BASE_STRINGS_STRING_PIECE_H_
  22. #define BASE_STRINGS_STRING_PIECE_H_
  23. #include <stddef.h>
  24. #include <iosfwd>
  25. #include <string>
  26. #include <type_traits>
  27. #include "base/base_export.h"
  28. #include "base/logging.h"
  29. #include "base/strings/char_traits.h"
  30. #include "base/strings/string16.h"
  31. #include "base/strings/string_piece_forward.h"
  32. namespace base {
  33. // internal --------------------------------------------------------------------
  34. // Many of the StringPiece functions use different implementations for the
  35. // 8-bit and 16-bit versions, and we don't want lots of template expansions in
  36. // this (very common) header that will slow down compilation.
  37. //
  38. // So here we define overloaded functions called by the StringPiece template.
  39. // For those that share an implementation, the two versions will expand to a
  40. // template internal to the .cc file.
  41. namespace internal {
  42. BASE_EXPORT size_t copy(const StringPiece& self,
  43. char* buf,
  44. size_t n,
  45. size_t pos);
  46. BASE_EXPORT size_t copy(const StringPiece16& self,
  47. char16* buf,
  48. size_t n,
  49. size_t pos);
  50. BASE_EXPORT size_t find(const StringPiece& self,
  51. const StringPiece& s,
  52. size_t pos);
  53. BASE_EXPORT size_t find(const StringPiece16& self,
  54. const StringPiece16& s,
  55. size_t pos);
  56. BASE_EXPORT size_t find(const StringPiece& self,
  57. char c,
  58. size_t pos);
  59. BASE_EXPORT size_t find(const StringPiece16& self,
  60. char16 c,
  61. size_t pos);
  62. BASE_EXPORT size_t rfind(const StringPiece& self,
  63. const StringPiece& s,
  64. size_t pos);
  65. BASE_EXPORT size_t rfind(const StringPiece16& self,
  66. const StringPiece16& s,
  67. size_t pos);
  68. BASE_EXPORT size_t rfind(const StringPiece& self,
  69. char c,
  70. size_t pos);
  71. BASE_EXPORT size_t rfind(const StringPiece16& self,
  72. char16 c,
  73. size_t pos);
  74. BASE_EXPORT size_t find_first_of(const StringPiece& self,
  75. const StringPiece& s,
  76. size_t pos);
  77. BASE_EXPORT size_t find_first_of(const StringPiece16& self,
  78. const StringPiece16& s,
  79. size_t pos);
  80. BASE_EXPORT size_t find_first_not_of(const StringPiece& self,
  81. const StringPiece& s,
  82. size_t pos);
  83. BASE_EXPORT size_t find_first_not_of(const StringPiece16& self,
  84. const StringPiece16& s,
  85. size_t pos);
  86. BASE_EXPORT size_t find_first_not_of(const StringPiece& self,
  87. char c,
  88. size_t pos);
  89. BASE_EXPORT size_t find_first_not_of(const StringPiece16& self,
  90. char16 c,
  91. size_t pos);
  92. BASE_EXPORT size_t find_last_of(const StringPiece& self,
  93. const StringPiece& s,
  94. size_t pos);
  95. BASE_EXPORT size_t find_last_of(const StringPiece16& self,
  96. const StringPiece16& s,
  97. size_t pos);
  98. BASE_EXPORT size_t find_last_of(const StringPiece& self,
  99. char c,
  100. size_t pos);
  101. BASE_EXPORT size_t find_last_of(const StringPiece16& self,
  102. char16 c,
  103. size_t pos);
  104. BASE_EXPORT size_t find_last_not_of(const StringPiece& self,
  105. const StringPiece& s,
  106. size_t pos);
  107. BASE_EXPORT size_t find_last_not_of(const StringPiece16& self,
  108. const StringPiece16& s,
  109. size_t pos);
  110. BASE_EXPORT size_t find_last_not_of(const StringPiece16& self,
  111. char16 c,
  112. size_t pos);
  113. BASE_EXPORT size_t find_last_not_of(const StringPiece& self,
  114. char c,
  115. size_t pos);
  116. BASE_EXPORT StringPiece substr(const StringPiece& self,
  117. size_t pos,
  118. size_t n);
  119. BASE_EXPORT StringPiece16 substr(const StringPiece16& self,
  120. size_t pos,
  121. size_t n);
  122. } // namespace internal
  123. // BasicStringPiece ------------------------------------------------------------
  124. // Defines the types, methods, operators, and data members common to both
  125. // StringPiece and StringPiece16.
  126. //
  127. // This is templatized by string class type rather than character type, so
  128. // BasicStringPiece<std::string> or BasicStringPiece<base::string16>.
  129. template <typename STRING_TYPE> class BasicStringPiece {
  130. public:
  131. // Standard STL container boilerplate.
  132. typedef size_t size_type;
  133. typedef typename STRING_TYPE::traits_type traits_type;
  134. typedef typename STRING_TYPE::value_type value_type;
  135. typedef const value_type* pointer;
  136. typedef const value_type& reference;
  137. typedef const value_type& const_reference;
  138. typedef ptrdiff_t difference_type;
  139. typedef const value_type* const_iterator;
  140. typedef std::reverse_iterator<const_iterator> const_reverse_iterator;
  141. static const size_type npos;
  142. public:
  143. // We provide non-explicit singleton constructors so users can pass
  144. // in a "const char*" or a "string" wherever a "StringPiece" is
  145. // expected (likewise for char16, string16, StringPiece16).
  146. constexpr BasicStringPiece() : ptr_(nullptr), length_(0) {}
  147. // TODO(crbug.com/1049498): Construction from nullptr is not allowed for
  148. // std::basic_string_view, so remove the special handling for it.
  149. // Note: This doesn't just use STRING_TYPE::traits_type::length(), since that
  150. // isn't constexpr until C++17.
  151. constexpr BasicStringPiece(const value_type* str)
  152. : ptr_(str), length_(!str ? 0 : CharTraits<value_type>::length(str)) {}
  153. // Explicitly disallow construction from nullptr. Note that this does not
  154. // catch construction from runtime strings that might be null.
  155. // Note: The following is just a more elaborate way of spelling
  156. // `BasicStringPiece(nullptr_t) = delete`, but unfortunately the terse form is
  157. // not supported by the PNaCl toolchain.
  158. // TODO(crbug.com/1049498): Remove once we CHECK(str) in the constructor
  159. // above.
  160. template <class T, class = std::enable_if_t<std::is_null_pointer<T>::value>>
  161. BasicStringPiece(T) {
  162. static_assert(sizeof(T) == 0, // Always false.
  163. "StringPiece does not support construction from nullptr, use "
  164. "the default constructor instead.");
  165. }
  166. BasicStringPiece(const STRING_TYPE& str)
  167. : ptr_(str.data()), length_(str.size()) {}
  168. constexpr BasicStringPiece(const value_type* offset, size_type len)
  169. : ptr_(offset), length_(len) {}
  170. BasicStringPiece(const typename STRING_TYPE::const_iterator& begin,
  171. const typename STRING_TYPE::const_iterator& end) {
  172. DCHECK(begin <= end) << "StringPiece iterators swapped or invalid.";
  173. length_ = static_cast<size_t>(std::distance(begin, end));
  174. // The length test before assignment is to avoid dereferencing an iterator
  175. // that may point to the end() of a string.
  176. ptr_ = length_ > 0 ? &*begin : nullptr;
  177. }
  178. // data() may return a pointer to a buffer with embedded NULs, and the
  179. // returned buffer may or may not be null terminated. Therefore it is
  180. // typically a mistake to pass data() to a routine that expects a NUL
  181. // terminated string.
  182. constexpr const value_type* data() const { return ptr_; }
  183. constexpr size_type size() const noexcept { return length_; }
  184. constexpr size_type length() const noexcept { return length_; }
  185. bool empty() const { return length_ == 0; }
  186. constexpr value_type operator[](size_type i) const {
  187. CHECK(i < length_);
  188. return ptr_[i];
  189. }
  190. value_type front() const {
  191. CHECK_NE(0UL, length_);
  192. return ptr_[0];
  193. }
  194. value_type back() const {
  195. CHECK_NE(0UL, length_);
  196. return ptr_[length_ - 1];
  197. }
  198. constexpr void remove_prefix(size_type n) {
  199. CHECK(n <= length_);
  200. ptr_ += n;
  201. length_ -= n;
  202. }
  203. constexpr void remove_suffix(size_type n) {
  204. CHECK(n <= length_);
  205. length_ -= n;
  206. }
  207. constexpr int compare(BasicStringPiece x) const noexcept {
  208. int r = CharTraits<value_type>::compare(
  209. ptr_, x.ptr_, (length_ < x.length_ ? length_ : x.length_));
  210. if (r == 0) {
  211. if (length_ < x.length_) r = -1;
  212. else if (length_ > x.length_) r = +1;
  213. }
  214. return r;
  215. }
  216. // This is the style of conversion preferred by std::string_view in C++17.
  217. explicit operator STRING_TYPE() const { return as_string(); }
  218. STRING_TYPE as_string() const {
  219. // std::string doesn't like to take a NULL pointer even with a 0 size.
  220. return empty() ? STRING_TYPE() : STRING_TYPE(data(), size());
  221. }
  222. const_iterator begin() const { return ptr_; }
  223. const_iterator end() const { return ptr_ + length_; }
  224. const_reverse_iterator rbegin() const {
  225. return const_reverse_iterator(ptr_ + length_);
  226. }
  227. const_reverse_iterator rend() const {
  228. return const_reverse_iterator(ptr_);
  229. }
  230. size_type max_size() const { return length_; }
  231. size_type capacity() const { return length_; }
  232. size_type copy(value_type* buf, size_type n, size_type pos = 0) const {
  233. return internal::copy(*this, buf, n, pos);
  234. }
  235. // Does "this" start with "x"
  236. constexpr bool starts_with(BasicStringPiece x) const noexcept {
  237. return (
  238. (this->length_ >= x.length_) &&
  239. (CharTraits<value_type>::compare(this->ptr_, x.ptr_, x.length_) == 0));
  240. }
  241. // Does "this" end with "x"
  242. constexpr bool ends_with(BasicStringPiece x) const noexcept {
  243. return ((this->length_ >= x.length_) &&
  244. (CharTraits<value_type>::compare(
  245. this->ptr_ + (this->length_ - x.length_), x.ptr_, x.length_) ==
  246. 0));
  247. }
  248. // find: Search for a character or substring at a given offset.
  249. size_type find(const BasicStringPiece<STRING_TYPE>& s,
  250. size_type pos = 0) const {
  251. return internal::find(*this, s, pos);
  252. }
  253. size_type find(value_type c, size_type pos = 0) const {
  254. return internal::find(*this, c, pos);
  255. }
  256. // rfind: Reverse find.
  257. size_type rfind(const BasicStringPiece& s,
  258. size_type pos = BasicStringPiece::npos) const {
  259. return internal::rfind(*this, s, pos);
  260. }
  261. size_type rfind(value_type c, size_type pos = BasicStringPiece::npos) const {
  262. return internal::rfind(*this, c, pos);
  263. }
  264. // find_first_of: Find the first occurence of one of a set of characters.
  265. size_type find_first_of(const BasicStringPiece& s,
  266. size_type pos = 0) const {
  267. return internal::find_first_of(*this, s, pos);
  268. }
  269. size_type find_first_of(value_type c, size_type pos = 0) const {
  270. return find(c, pos);
  271. }
  272. // find_first_not_of: Find the first occurence not of a set of characters.
  273. size_type find_first_not_of(const BasicStringPiece& s,
  274. size_type pos = 0) const {
  275. return internal::find_first_not_of(*this, s, pos);
  276. }
  277. size_type find_first_not_of(value_type c, size_type pos = 0) const {
  278. return internal::find_first_not_of(*this, c, pos);
  279. }
  280. // find_last_of: Find the last occurence of one of a set of characters.
  281. size_type find_last_of(const BasicStringPiece& s,
  282. size_type pos = BasicStringPiece::npos) const {
  283. return internal::find_last_of(*this, s, pos);
  284. }
  285. size_type find_last_of(value_type c,
  286. size_type pos = BasicStringPiece::npos) const {
  287. return rfind(c, pos);
  288. }
  289. // find_last_not_of: Find the last occurence not of a set of characters.
  290. size_type find_last_not_of(const BasicStringPiece& s,
  291. size_type pos = BasicStringPiece::npos) const {
  292. return internal::find_last_not_of(*this, s, pos);
  293. }
  294. size_type find_last_not_of(value_type c,
  295. size_type pos = BasicStringPiece::npos) const {
  296. return internal::find_last_not_of(*this, c, pos);
  297. }
  298. // substr.
  299. BasicStringPiece substr(size_type pos,
  300. size_type n = BasicStringPiece::npos) const {
  301. return internal::substr(*this, pos, n);
  302. }
  303. protected:
  304. const value_type* ptr_;
  305. size_type length_;
  306. };
  307. template <typename STRING_TYPE>
  308. const typename BasicStringPiece<STRING_TYPE>::size_type
  309. BasicStringPiece<STRING_TYPE>::npos =
  310. typename BasicStringPiece<STRING_TYPE>::size_type(-1);
  311. // MSVC doesn't like complex extern templates and DLLs.
  312. #if !defined(COMPILER_MSVC)
  313. extern template class BASE_EXPORT BasicStringPiece<std::string>;
  314. extern template class BASE_EXPORT BasicStringPiece<string16>;
  315. #endif
  316. // Comparison operators --------------------------------------------------------
  317. // operator ==
  318. template <typename StringT>
  319. constexpr bool operator==(BasicStringPiece<StringT> lhs,
  320. BasicStringPiece<StringT> rhs) noexcept {
  321. return lhs.size() == rhs.size() && lhs.compare(rhs) == 0;
  322. }
  323. // Here and below we make use of std::common_type_t to emulate an identity type
  324. // transformation. This creates a non-deduced context, so that we can compare
  325. // StringPieces with types that implicitly convert to StringPieces. See
  326. // https://wg21.link/n3766 for details.
  327. // Furthermore, we require dummy template parameters for these overloads to work
  328. // around a name mangling issue on Windows.
  329. template <typename StringT, int = 1>
  330. constexpr bool operator==(
  331. BasicStringPiece<StringT> lhs,
  332. std::common_type_t<BasicStringPiece<StringT>> rhs) noexcept {
  333. return lhs.size() == rhs.size() && lhs.compare(rhs) == 0;
  334. }
  335. template <typename StringT, int = 2>
  336. constexpr bool operator==(std::common_type_t<BasicStringPiece<StringT>> lhs,
  337. BasicStringPiece<StringT> rhs) noexcept {
  338. return lhs.size() == rhs.size() && lhs.compare(rhs) == 0;
  339. }
  340. // operator !=
  341. template <typename StringT>
  342. constexpr bool operator!=(BasicStringPiece<StringT> lhs,
  343. BasicStringPiece<StringT> rhs) noexcept {
  344. return !(lhs == rhs);
  345. }
  346. template <typename StringT, int = 1>
  347. constexpr bool operator!=(
  348. BasicStringPiece<StringT> lhs,
  349. std::common_type_t<BasicStringPiece<StringT>> rhs) noexcept {
  350. return !(lhs == rhs);
  351. }
  352. template <typename StringT, int = 2>
  353. constexpr bool operator!=(std::common_type_t<BasicStringPiece<StringT>> lhs,
  354. BasicStringPiece<StringT> rhs) noexcept {
  355. return !(lhs == rhs);
  356. }
  357. // operator <
  358. template <typename StringT>
  359. constexpr bool operator<(BasicStringPiece<StringT> lhs,
  360. BasicStringPiece<StringT> rhs) noexcept {
  361. return lhs.compare(rhs) < 0;
  362. }
  363. template <typename StringT, int = 1>
  364. constexpr bool operator<(
  365. BasicStringPiece<StringT> lhs,
  366. std::common_type_t<BasicStringPiece<StringT>> rhs) noexcept {
  367. return lhs.compare(rhs) < 0;
  368. }
  369. template <typename StringT, int = 2>
  370. constexpr bool operator<(std::common_type_t<BasicStringPiece<StringT>> lhs,
  371. BasicStringPiece<StringT> rhs) noexcept {
  372. return lhs.compare(rhs) < 0;
  373. }
  374. // operator >
  375. template <typename StringT>
  376. constexpr bool operator>(BasicStringPiece<StringT> lhs,
  377. BasicStringPiece<StringT> rhs) noexcept {
  378. return rhs < lhs;
  379. }
  380. template <typename StringT, int = 1>
  381. constexpr bool operator>(
  382. BasicStringPiece<StringT> lhs,
  383. std::common_type_t<BasicStringPiece<StringT>> rhs) noexcept {
  384. return rhs < lhs;
  385. }
  386. template <typename StringT, int = 2>
  387. constexpr bool operator>(std::common_type_t<BasicStringPiece<StringT>> lhs,
  388. BasicStringPiece<StringT> rhs) noexcept {
  389. return rhs < lhs;
  390. }
  391. // operator <=
  392. template <typename StringT>
  393. constexpr bool operator<=(BasicStringPiece<StringT> lhs,
  394. BasicStringPiece<StringT> rhs) noexcept {
  395. return !(rhs < lhs);
  396. }
  397. template <typename StringT, int = 1>
  398. constexpr bool operator<=(
  399. BasicStringPiece<StringT> lhs,
  400. std::common_type_t<BasicStringPiece<StringT>> rhs) noexcept {
  401. return !(rhs < lhs);
  402. }
  403. template <typename StringT, int = 2>
  404. constexpr bool operator<=(std::common_type_t<BasicStringPiece<StringT>> lhs,
  405. BasicStringPiece<StringT> rhs) noexcept {
  406. return !(rhs < lhs);
  407. }
  408. // operator >=
  409. template <typename StringT>
  410. constexpr bool operator>=(BasicStringPiece<StringT> lhs,
  411. BasicStringPiece<StringT> rhs) noexcept {
  412. return !(lhs < rhs);
  413. }
  414. template <typename StringT, int = 1>
  415. constexpr bool operator>=(
  416. BasicStringPiece<StringT> lhs,
  417. std::common_type_t<BasicStringPiece<StringT>> rhs) noexcept {
  418. return !(lhs < rhs);
  419. }
  420. template <typename StringT, int = 2>
  421. constexpr bool operator>=(std::common_type_t<BasicStringPiece<StringT>> lhs,
  422. BasicStringPiece<StringT> rhs) noexcept {
  423. return !(lhs < rhs);
  424. }
  425. BASE_EXPORT std::ostream& operator<<(std::ostream& o,
  426. const StringPiece& piece);
  427. BASE_EXPORT std::ostream& operator<<(std::ostream& o,
  428. const StringPiece16& piece);
  429. // Hashing ---------------------------------------------------------------------
  430. // We provide appropriate hash functions so StringPiece and StringPiece16 can
  431. // be used as keys in hash sets and maps.
  432. // This hash function is copied from base/strings/string16.h. We don't use the
  433. // ones already defined for string and string16 directly because it would
  434. // require the string constructors to be called, which we don't want.
  435. template <typename StringPieceType>
  436. struct StringPieceHashImpl {
  437. std::size_t operator()(StringPieceType sp) const {
  438. std::size_t result = 0;
  439. for (auto c : sp)
  440. result = (result * 131) + c;
  441. return result;
  442. }
  443. };
  444. using StringPieceHash = StringPieceHashImpl<StringPiece>;
  445. using StringPiece16Hash = StringPieceHashImpl<StringPiece16>;
  446. using WStringPieceHash = StringPieceHashImpl<WStringPiece>;
  447. } // namespace base
  448. #endif // BASE_STRINGS_STRING_PIECE_H_