89 lines
2.8 KiB
C++
89 lines
2.8 KiB
C++
#pragma once
|
|
#include <utempl/module.hpp>
|
|
#ifdef UTEMPL_MODULE
|
|
export module utempl.string;
|
|
import std;
|
|
#else
|
|
#include <algorithm>
|
|
#include <string>
|
|
#endif
|
|
|
|
UTEMPL_EXPORT_BEGIN
|
|
|
|
namespace utempl {
|
|
template <std::size_t Size>
|
|
struct ConstexprString {
|
|
std::array<char, Size> data;
|
|
using char_type = char;
|
|
constexpr auto begin() -> char* {
|
|
return this->data.begin();
|
|
};
|
|
[[nodiscard]] constexpr auto begin() const -> const char* {
|
|
return this->data.begin();
|
|
};
|
|
[[nodiscard]] constexpr auto end() -> char* {
|
|
return this->data.end();
|
|
};
|
|
[[nodiscard]] constexpr auto end() const -> const char* {
|
|
return this->data.end();
|
|
};
|
|
static constexpr auto kSize = Size == 0 ? 0 : Size - 1;
|
|
explicit constexpr ConstexprString() = default;
|
|
constexpr ConstexprString(const char (&data)[Size]) : data{} { // NOLINT
|
|
std::ranges::copy_n(data, Size, this->data.begin());
|
|
};
|
|
explicit constexpr ConstexprString(std::string_view data) : data{} {
|
|
std::ranges::copy_n(data.begin(), Size, this->data.begin());
|
|
};
|
|
explicit constexpr ConstexprString(std::array<char, Size> data) : data(std::move(data)) {};
|
|
constexpr auto size() const {
|
|
return Size == 0 ? 0 : Size - 1;
|
|
};
|
|
constexpr operator std::string_view() const& { // NOLINT
|
|
return {this->begin()};
|
|
};
|
|
constexpr auto operator==(std::string_view other) const -> bool {
|
|
return static_cast<std::string_view>(*this) == other;
|
|
};
|
|
constexpr auto operator==(const ConstexprString<Size>& other) const {
|
|
return static_cast<std::string_view>(*this) == static_cast<std::string_view>(other);
|
|
};
|
|
template <std::size_t SSize>
|
|
constexpr auto operator==(const ConstexprString<SSize>& other) const -> bool {
|
|
return false;
|
|
};
|
|
constexpr auto operator==(const std::string& other) const -> bool {
|
|
return static_cast<std::string_view>(*this) == other;
|
|
};
|
|
template <std::size_t SSize>
|
|
constexpr auto operator+(const ConstexprString<SSize>& other) -> ConstexprString<Size + SSize - 1> {
|
|
ConstexprString<Size + SSize - 1> response;
|
|
std::ranges::copy_n(this->begin(), Size - 1, response.begin());
|
|
std::ranges::copy_n(other.begin(), SSize, response.begin() + Size - 1);
|
|
return response;
|
|
};
|
|
constexpr ConstexprString(const ConstexprString&) = default;
|
|
constexpr ConstexprString(ConstexprString&&) = default;
|
|
};
|
|
|
|
template <std::size_t N>
|
|
constexpr auto operator<<(std::ostream& stream, const ConstexprString<N>& str) -> std::ostream& {
|
|
stream << static_cast<std::string_view>(str);
|
|
return stream;
|
|
};
|
|
|
|
template <std::size_t Count>
|
|
constexpr auto CreateStringWith(char c) {
|
|
ConstexprString<Count + 1> str{};
|
|
for(std::size_t i = 0; i < Count; i++) {
|
|
str.data[i] = c;
|
|
};
|
|
str.data[Count] = '\0';
|
|
return str;
|
|
};
|
|
|
|
template <std::size_t Size>
|
|
ConstexprString(const char (&data)[Size]) -> ConstexprString<Size>; // NOLINT
|
|
} // namespace utempl
|
|
|
|
UTEMPL_EXPORT_END
|