Skip to content

Commit

Permalink
[libc++][strings] P2591R5: Concatenation of strings and string views (#…
Browse files Browse the repository at this point in the history
…88389)

Summary:
Implemented: https://wg21.link/P2591R5
- https://eel.is/c++draft/string.syn
- https://eel.is/c++draft/string.op.plus

---------

Co-authored-by: Hristo Hristov <[email protected]>

Test Plan: 

Reviewers: 

Subscribers: 

Tasks: 

Tags: 


Differential Revision: https://phabricator.intern.facebook.com/D60250903
  • Loading branch information
H-G-Hristov authored and yuxuanchen1997 committed Jul 25, 2024
1 parent 367d148 commit 620b41e
Show file tree
Hide file tree
Showing 10 changed files with 332 additions and 9 deletions.
2 changes: 2 additions & 0 deletions libcxx/docs/FeatureTestMacroTable.rst
Original file line number Diff line number Diff line change
Expand Up @@ -474,6 +474,8 @@ Status
---------------------------------------------------------- -----------------
``__cpp_lib_sstream_from_string_view`` ``202306L``
---------------------------------------------------------- -----------------
``__cpp_lib_string_view`` ``202403L``
---------------------------------------------------------- -----------------
``__cpp_lib_submdspan`` *unimplemented*
---------------------------------------------------------- -----------------
``__cpp_lib_text_encoding`` *unimplemented*
Expand Down
1 change: 1 addition & 0 deletions libcxx/docs/ReleaseNotes/19.rst
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ Implemented Papers
- P2872R3 - Remove ``wstring_convert`` From C++26
- P3142R0 - Printing Blank Lines with ``println`` (as DR against C++23)
- P2944R3 - Comparisons for ``reference_wrapper`` (comparison operators for ``reference_wrapper`` only)
- P2591R5 - Concatenation of strings and string views
- P2968R2 - Make ``std::ignore`` a first-class object
- P2302R4 - ``std::ranges::contains``
- P1659R3 - ``std::ranges::starts_with`` and ``std::ranges::ends_with``
Expand Down
2 changes: 1 addition & 1 deletion libcxx/docs/Status/Cxx2cPapers.csv
Original file line number Diff line number Diff line change
Expand Up @@ -55,7 +55,7 @@
"`P2845R8 <https://wg21.link/P2845R8>`__","LWG","Formatting of ``std::filesystem::path``","Tokyo March 2024","","","|format|"
"`P0493R5 <https://wg21.link/P0493R5>`__","LWG","Atomic minimum/maximum","Tokyo March 2024","","",""
"`P2542R8 <https://wg21.link/P2542R8>`__","LWG","``views::concat``","Tokyo March 2024","","","|ranges|"
"`P2591R5 <https://wg21.link/P2591R5>`__","LWG","Concatenation of strings and string views","Tokyo March 2024","","",""
"`P2591R5 <https://wg21.link/P2591R5>`__","LWG","Concatenation of strings and string views","Tokyo March 2024","|Complete|","19.0",""
"`P2248R8 <https://wg21.link/P2248R8>`__","LWG","Enabling list-initialization for algorithms","Tokyo March 2024","","",""
"`P2810R4 <https://wg21.link/P2810R4>`__","LWG","``is_debugger_present`` ``is_replaceable``","Tokyo March 2024","","",""
"`P1068R11 <https://wg21.link/P1068R11>`__","LWG","Vector API for random number generation","Tokyo March 2024","","",""
Expand Down
98 changes: 98 additions & 0 deletions libcxx/include/string
Original file line number Diff line number Diff line change
Expand Up @@ -407,6 +407,24 @@ template<class charT, class traits, class Allocator>
basic_string<charT, traits, Allocator>
operator+(const basic_string<charT, traits, Allocator>& lhs, charT rhs); // constexpr since C++20
template<class charT, class traits, class Allocator>
constexpr basic_string<charT, traits, Allocator>
operator+(const basic_string<charT, traits, Allocator>& lhs,
type_identity_t<basic_string_view<charT, traits>> rhs); // Since C++26
template<class charT, class traits, class Allocator>
constexpr basic_string<charT, traits, Allocator>
operator+(basic_string<charT, traits, Allocator>&& lhs,
type_identity_t<basic_string_view<charT, traits>> rhs); // Since C++26
template<class charT, class traits, class Allocator>
constexpr basic_string<charT, traits, Allocator>
operator+(type_identity_t<basic_string_view<charT, traits>> lhs,
const basic_string<charT, traits, Allocator>& rhs); // Since C++26
template<class charT, class traits, class Allocator>
constexpr basic_string<charT, traits, Allocator>
operator+(type_identity_t<basic_string_view<charT, traits>> lhs,
basic_string<charT, traits, Allocator>&& rhs); // Since C++26
template<class charT, class traits, class Allocator>
bool operator==(const basic_string<charT, traits, Allocator>& lhs,
const basic_string<charT, traits, Allocator>& rhs) noexcept; // constexpr since C++20
Expand Down Expand Up @@ -687,6 +705,28 @@ template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR_SINCE_CXX20 basic_string<_CharT, _Traits, _Allocator>
operator+(const basic_string<_CharT, _Traits, _Allocator>& __x, _CharT __y);

#if _LIBCPP_STD_VER >= 26

template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI constexpr basic_string<_CharT, _Traits, _Allocator>
operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
type_identity_t<basic_string_view<_CharT, _Traits>> __rhs);

template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI constexpr basic_string<_CharT, _Traits, _Allocator>
operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, type_identity_t<basic_string_view<_CharT, _Traits>> __rhs);

template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI constexpr basic_string<_CharT, _Traits, _Allocator>
operator+(type_identity_t<basic_string_view<_CharT, _Traits>> __lhs,
const basic_string<_CharT, _Traits, _Allocator>& __rhs);

template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI constexpr basic_string<_CharT, _Traits, _Allocator>
operator+(type_identity_t<basic_string_view<_CharT, _Traits>> __lhs, basic_string<_CharT, _Traits, _Allocator>&& __rhs);

#endif

extern template _LIBCPP_EXPORTED_FROM_ABI string operator+
<char, char_traits<char>, allocator<char> >(char const*, string const&);

Expand Down Expand Up @@ -2150,6 +2190,10 @@ private:
friend _LIBCPP_CONSTEXPR_SINCE_CXX20 basic_string operator+ <>(value_type, const basic_string&);
friend _LIBCPP_CONSTEXPR_SINCE_CXX20 basic_string operator+ <>(const basic_string&, const value_type*);
friend _LIBCPP_CONSTEXPR_SINCE_CXX20 basic_string operator+ <>(const basic_string&, value_type);
#if _LIBCPP_STD_VER >= 26
friend constexpr basic_string operator+ <>(const basic_string&, type_identity_t<__self_view>);
friend constexpr basic_string operator+ <>(type_identity_t<__self_view>, const basic_string&);
#endif
};

// These declarations must appear before any functions are implicitly used
Expand Down Expand Up @@ -4007,6 +4051,60 @@ operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs, _CharT __rhs) {

#endif // _LIBCPP_CXX03_LANG

#if _LIBCPP_STD_VER >= 26

template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI constexpr basic_string<_CharT, _Traits, _Allocator>
operator+(const basic_string<_CharT, _Traits, _Allocator>& __lhs,
type_identity_t<basic_string_view<_CharT, _Traits>> __rhs) {
using _String = basic_string<_CharT, _Traits, _Allocator>;
typename _String::size_type __lhs_sz = __lhs.size();
typename _String::size_type __rhs_sz = __rhs.size();
_String __r(__uninitialized_size_tag(),
__lhs_sz + __rhs_sz,
_String::__alloc_traits::select_on_container_copy_construction(__lhs.get_allocator()));
auto __ptr = std::__to_address(__r.__get_pointer());
_Traits::copy(__ptr, __lhs.data(), __lhs_sz);
_Traits::copy(__ptr + __lhs_sz, __rhs.data(), __rhs_sz);
_Traits::assign(__ptr + __lhs_sz + __rhs_sz, 1, _CharT());
return __r;
}

template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI constexpr basic_string<_CharT, _Traits, _Allocator>
operator+(basic_string<_CharT, _Traits, _Allocator>&& __lhs,
type_identity_t<basic_string_view<_CharT, _Traits>> __rhs) {
__lhs.append(__rhs);
return std::move(__lhs);
}

template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI constexpr basic_string<_CharT, _Traits, _Allocator>
operator+(type_identity_t<basic_string_view<_CharT, _Traits>> __lhs,
const basic_string<_CharT, _Traits, _Allocator>& __rhs) {
using _String = basic_string<_CharT, _Traits, _Allocator>;
typename _String::size_type __lhs_sz = __lhs.size();
typename _String::size_type __rhs_sz = __rhs.size();
_String __r(__uninitialized_size_tag(),
__lhs_sz + __rhs_sz,
_String::__alloc_traits::select_on_container_copy_construction(__rhs.get_allocator()));
auto __ptr = std::__to_address(__r.__get_pointer());
_Traits::copy(__ptr, __lhs.data(), __lhs_sz);
_Traits::copy(__ptr + __lhs_sz, __rhs.data(), __rhs_sz);
_Traits::assign(__ptr + __lhs_sz + __rhs_sz, 1, _CharT());
return __r;
}

template <class _CharT, class _Traits, class _Allocator>
_LIBCPP_HIDE_FROM_ABI constexpr basic_string<_CharT, _Traits, _Allocator>
operator+(type_identity_t<basic_string_view<_CharT, _Traits>> __lhs,
basic_string<_CharT, _Traits, _Allocator>&& __rhs) {
__rhs.insert(0, __lhs);
return std::move(__rhs);
}

#endif // _LIBCPP_STD_VER >= 26

// swap

template <class _CharT, class _Traits, class _Allocator>
Expand Down
5 changes: 4 additions & 1 deletion libcxx/include/version
Original file line number Diff line number Diff line change
Expand Up @@ -231,7 +231,8 @@ __cpp_lib_stdatomic_h 202011L <stdatomic.h>
__cpp_lib_string_contains 202011L <string> <string_view>
__cpp_lib_string_resize_and_overwrite 202110L <string>
__cpp_lib_string_udls 201304L <string>
__cpp_lib_string_view 201803L <string> <string_view>
__cpp_lib_string_view 202403L <string> <string_view>
201803L // C++20
201606L // C++17
__cpp_lib_submdspan 202306L <mdspan>
__cpp_lib_syncbuf 201803L <syncstream>
Expand Down Expand Up @@ -547,6 +548,8 @@ __cpp_lib_void_t 201411L <type_traits>
# define __cpp_lib_span_at 202311L
# define __cpp_lib_span_initializer_list 202311L
# define __cpp_lib_sstream_from_string_view 202306L
# undef __cpp_lib_string_view
# define __cpp_lib_string_view 202403L
// # define __cpp_lib_submdspan 202306L
// # define __cpp_lib_text_encoding 202306L
# undef __cpp_lib_to_chars
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@
__cpp_lib_string_udls 201304L [C++14]
__cpp_lib_string_view 201606L [C++17]
201803L [C++20]
202403L [C++26]
__cpp_lib_to_string 202306L [C++26]
*/

Expand Down Expand Up @@ -483,8 +484,8 @@
# ifndef __cpp_lib_string_view
# error "__cpp_lib_string_view should be defined in c++26"
# endif
# if __cpp_lib_string_view != 201803L
# error "__cpp_lib_string_view should have the value 201803L in c++26"
# if __cpp_lib_string_view != 202403L
# error "__cpp_lib_string_view should have the value 202403L in c++26"
# endif

# if !defined(_LIBCPP_VERSION)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
__cpp_lib_string_contains 202011L [C++23]
__cpp_lib_string_view 201606L [C++17]
201803L [C++20]
202403L [C++26]
*/

#include <string_view>
Expand Down Expand Up @@ -252,8 +253,8 @@
# ifndef __cpp_lib_string_view
# error "__cpp_lib_string_view should be defined in c++26"
# endif
# if __cpp_lib_string_view != 201803L
# error "__cpp_lib_string_view should have the value 201803L in c++26"
# if __cpp_lib_string_view != 202403L
# error "__cpp_lib_string_view should have the value 202403L in c++26"
# endif

#endif // TEST_STD_VER > 23
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,7 @@
__cpp_lib_string_udls 201304L [C++14]
__cpp_lib_string_view 201606L [C++17]
201803L [C++20]
202403L [C++26]
__cpp_lib_submdspan 202306L [C++26]
__cpp_lib_syncbuf 201803L [C++20]
__cpp_lib_text_encoding 202306L [C++26]
Expand Down Expand Up @@ -7894,8 +7895,8 @@
# ifndef __cpp_lib_string_view
# error "__cpp_lib_string_view should be defined in c++26"
# endif
# if __cpp_lib_string_view != 201803L
# error "__cpp_lib_string_view should have the value 201803L in c++26"
# if __cpp_lib_string_view != 202403L
# error "__cpp_lib_string_view should have the value 202403L in c++26"
# endif

# if !defined(_LIBCPP_VERSION)
Expand Down
Loading

0 comments on commit 620b41e

Please sign in to comment.