#ifndef SPROUT_STRING_CONCAT_HPP #define SPROUT_STRING_CONCAT_HPP #include #include #include #include #include #include namespace sprout { namespace detail { template inline SPROUT_CONSTEXPR sprout::basic_string string_concat( sprout::basic_string const& lhs, std::size_t lsize, T const& rhs, sprout::index_tuple ) { return sprout::basic_string{ { (Indexes < lsize ? lhs[Indexes] : Indexes < lsize + 1 ? rhs : T() )... }, lsize + 1 }; } template inline SPROUT_CONSTEXPR sprout::basic_string string_concat( T const& lhs, sprout::basic_string const& rhs, std::size_t rsize, sprout::index_tuple ) { return sprout::basic_string{ { (Indexes < 1 ? lhs : Indexes < 1 + rsize ? rhs[Indexes - 1] : T() )... }, 1 + rsize }; } template inline SPROUT_CONSTEXPR sprout::basic_string string_concat( sprout::basic_string const& lhs, std::size_t lsize, T const (& rhs)[M], std::size_t rsize, sprout::index_tuple ) { return sprout::basic_string{ { (Indexes < lsize ? lhs[Indexes] : Indexes < lsize + rsize ? rhs[Indexes - lsize] : T() )... }, lsize + rsize }; } template inline SPROUT_CONSTEXPR sprout::basic_string string_concat( T const (& lhs)[M], std::size_t lsize, sprout::basic_string const& rhs, std::size_t rsize, sprout::index_tuple ) { return sprout::basic_string{ { (Indexes < lsize ? lhs[Indexes] : Indexes < lsize + rsize ? rhs[Indexes - lsize] : T() )... }, lsize + rsize }; } template inline SPROUT_CONSTEXPR sprout::basic_string string_concat( sprout::basic_string const& lhs, std::size_t lsize, sprout::basic_string const& rhs, std::size_t rsize, sprout::index_tuple ) { return sprout::basic_string{ { (Indexes < lsize ? lhs[Indexes] : Indexes < lsize + rsize ? rhs[Indexes - lsize] : T() )... }, lsize + rsize }; } } // namespace detail // // operator+ // template inline SPROUT_CONSTEXPR sprout::basic_string operator+(sprout::basic_string const& lhs, T const& rhs) { return sprout::detail::string_concat( lhs, lhs.size(), rhs, sprout::make_index_tuple::make() ); } template inline SPROUT_CONSTEXPR sprout::basic_string operator+(T const& lhs, sprout::basic_string const& rhs) { return sprout::detail::string_concat( lhs, rhs, rhs.size(), sprout::make_index_tuple<1 + N>::make() ); } template inline SPROUT_CONSTEXPR sprout::basic_string operator+(sprout::basic_string const& lhs, T const (& rhs)[M]) { typedef sprout::char_traits_helper traits_type; return sprout::detail::string_concat( lhs, lhs.size(), rhs, traits_type::length(rhs, M - 1), sprout::make_index_tuple::make() ); } template inline SPROUT_CONSTEXPR sprout::basic_string operator+(T const (& lhs)[M], sprout::basic_string const& rhs) { typedef sprout::char_traits_helper traits_type; return sprout::detail::string_concat( lhs, traits_type::length(lhs, M - 1), rhs, rhs.size(), sprout::make_index_tuple<(M - 1) + N>::make() ); } template inline SPROUT_CONSTEXPR sprout::basic_string operator+(sprout::basic_string const& lhs, sprout::basic_string const& rhs) { return sprout::detail::string_concat( lhs, lhs.size(), rhs, rhs.size(), sprout::make_index_tuple::make() ); } } // namespace sprout #endif // #ifndef SPROUT_STRING_CONCAT_HPP