BAN: Mark some class methods as constexpr

This commit is contained in:
Bananymous 2024-05-28 01:07:29 +03:00
parent a1ab44d39f
commit f5987b68ff
3 changed files with 100 additions and 96 deletions

View File

@ -9,7 +9,7 @@ namespace BAN
{ {
template<typename It> template<typename It>
It next(It it, size_t count) constexpr It next(It it, size_t count)
{ {
for (size_t i = 0; i < count; i++) for (size_t i = 0; i < count; i++)
++it; ++it;
@ -18,13 +18,13 @@ namespace BAN
template<typename It> template<typename It>
requires requires(It it, size_t n) { requires is_same_v<decltype(it + n), It>; } requires requires(It it, size_t n) { requires is_same_v<decltype(it + n), It>; }
It next(It it, size_t count) constexpr It next(It it, size_t count)
{ {
return it + count; return it + count;
} }
template<typename It> template<typename It>
It prev(It it, size_t count) constexpr It prev(It it, size_t count)
{ {
for (size_t i = 0; i < count; i++) for (size_t i = 0; i < count; i++)
--it; --it;
@ -33,13 +33,13 @@ namespace BAN
template<typename It> template<typename It>
requires requires(It it, size_t n) { requires is_same_v<decltype(it - n), It>; } requires requires(It it, size_t n) { requires is_same_v<decltype(it - n), It>; }
It prev(It it, size_t count) constexpr It prev(It it, size_t count)
{ {
return it - count; return it - count;
} }
template<typename It> template<typename It>
size_t distance(It it1, It it2) constexpr size_t distance(It it1, It it2)
{ {
size_t dist = 0; size_t dist = 0;
while (it1 != it2) while (it1 != it2)
@ -52,7 +52,7 @@ namespace BAN
template<typename It> template<typename It>
requires requires(It it1, It it2) { requires is_integral_v<decltype(it2 - it1)>; } requires requires(It it1, It it2) { requires is_integral_v<decltype(it2 - it1)>; }
size_t distance(It it1, It it2) constexpr size_t distance(It it1, It it2)
{ {
return it2 - it1; return it2 - it1;
} }
@ -64,109 +64,109 @@ namespace BAN
using value_type = T; using value_type = T;
public: public:
IteratorSimpleGeneral() = default; constexpr IteratorSimpleGeneral() = default;
template<bool CONST2, typename = enable_if_t<CONST2 == CONST || CONST>> template<bool CONST2, typename = enable_if_t<CONST2 == CONST || CONST>>
IteratorSimpleGeneral(const IteratorSimpleGeneral<T, Container, CONST2>& other) constexpr IteratorSimpleGeneral(const IteratorSimpleGeneral<T, Container, CONST2>& other)
: m_pointer(other.m_pointer) : m_pointer(other.m_pointer)
, m_valid(other.m_valid) , m_valid(other.m_valid)
{ {
} }
const T& operator*() const constexpr const T& operator*() const
{ {
ASSERT(m_pointer); ASSERT(m_pointer);
return *m_pointer; return *m_pointer;
} }
template<bool CONST2 = CONST> template<bool CONST2 = CONST>
enable_if_t<!CONST2, T&> operator*() constexpr enable_if_t<!CONST2, T&> operator*()
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_pointer); ASSERT(m_pointer);
return *m_pointer; return *m_pointer;
} }
const T* operator->() const constexpr const T* operator->() const
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_pointer); ASSERT(m_pointer);
return m_pointer; return m_pointer;
} }
template<bool CONST2 = CONST> template<bool CONST2 = CONST>
enable_if_t<!CONST2, T*> operator->() constexpr enable_if_t<!CONST2, T*> operator->()
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_pointer); ASSERT(m_pointer);
return m_pointer; return m_pointer;
} }
IteratorSimpleGeneral& operator++() constexpr IteratorSimpleGeneral& operator++()
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_pointer); ASSERT(m_pointer);
++m_pointer; ++m_pointer;
return *this; return *this;
} }
IteratorSimpleGeneral operator++(int) constexpr IteratorSimpleGeneral operator++(int)
{ {
auto temp = *this; auto temp = *this;
++(*this); ++(*this);
return temp; return temp;
} }
IteratorSimpleGeneral& operator--() constexpr IteratorSimpleGeneral& operator--()
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_pointer); ASSERT(m_pointer);
--m_pointer; --m_pointer;
return *this; return *this;
} }
IteratorSimpleGeneral operator--(int) constexpr IteratorSimpleGeneral operator--(int)
{ {
auto temp = *this; auto temp = *this;
--(*this); --(*this);
return temp; return temp;
} }
size_t operator-(const IteratorSimpleGeneral& other) const constexpr size_t operator-(const IteratorSimpleGeneral& other) const
{ {
ASSERT(*this && other); ASSERT(*this && other);
return m_pointer - other.m_pointer; return m_pointer - other.m_pointer;
} }
IteratorSimpleGeneral operator+(size_t offset) const constexpr IteratorSimpleGeneral operator+(size_t offset) const
{ {
return IteratorSimpleGeneral(m_pointer + offset); return IteratorSimpleGeneral(m_pointer + offset);
} }
IteratorSimpleGeneral operator-(size_t offset) const constexpr IteratorSimpleGeneral operator-(size_t offset) const
{ {
return IteratorSimpleGeneral(m_pointer - offset); return IteratorSimpleGeneral(m_pointer - offset);
} }
bool operator<(const IteratorSimpleGeneral& other) const constexpr bool operator<(const IteratorSimpleGeneral& other) const
{ {
ASSERT(*this); ASSERT(*this);
return m_pointer < other.m_pointer; return m_pointer < other.m_pointer;
} }
bool operator==(const IteratorSimpleGeneral& other) const constexpr bool operator==(const IteratorSimpleGeneral& other) const
{ {
ASSERT(*this); ASSERT(*this);
return m_pointer == other.m_pointer; return m_pointer == other.m_pointer;
} }
bool operator!=(const IteratorSimpleGeneral& other) const constexpr bool operator!=(const IteratorSimpleGeneral& other) const
{ {
ASSERT(*this); ASSERT(*this);
return !(*this == other); return !(*this == other);
} }
explicit operator bool() const constexpr explicit operator bool() const
{ {
return m_valid; return m_valid;
} }
private: private:
IteratorSimpleGeneral(maybe_const_t<CONST, T>* pointer) constexpr IteratorSimpleGeneral(maybe_const_t<CONST, T>* pointer)
: m_pointer(pointer) : m_pointer(pointer)
, m_valid(true) , m_valid(true)
{ {
@ -193,16 +193,16 @@ namespace BAN
using value_type = T; using value_type = T;
public: public:
IteratorDoubleGeneral() = default; constexpr IteratorDoubleGeneral() = default;
template<bool CONST2, typename = enable_if_t<CONST2 == CONST || CONST>> template<bool CONST2, typename = enable_if_t<CONST2 == CONST || CONST>>
IteratorDoubleGeneral(const IteratorDoubleGeneral<T, OuterContainer, InnerContainer, Container, CONST2>& other) constexpr IteratorDoubleGeneral(const IteratorDoubleGeneral<T, OuterContainer, InnerContainer, Container, CONST2>& other)
: m_outer_end(other.m_outer_end) : m_outer_end(other.m_outer_end)
, m_outer_current(other.m_outer_current) , m_outer_current(other.m_outer_current)
, m_inner_current(other.m_inner_current) , m_inner_current(other.m_inner_current)
{ {
} }
const T& operator*() const constexpr const T& operator*() const
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_outer_current != m_outer_end); ASSERT(m_outer_current != m_outer_end);
@ -210,7 +210,7 @@ namespace BAN
return m_inner_current.operator*(); return m_inner_current.operator*();
} }
template<bool CONST2 = CONST> template<bool CONST2 = CONST>
enable_if_t<!CONST2, T&> operator*() constexpr enable_if_t<!CONST2, T&> operator*()
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_outer_current != m_outer_end); ASSERT(m_outer_current != m_outer_end);
@ -218,7 +218,7 @@ namespace BAN
return m_inner_current.operator*(); return m_inner_current.operator*();
} }
const T* operator->() const constexpr const T* operator->() const
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_outer_current != m_outer_end); ASSERT(m_outer_current != m_outer_end);
@ -226,7 +226,7 @@ namespace BAN
return m_inner_current.operator->(); return m_inner_current.operator->();
} }
template<bool CONST2 = CONST> template<bool CONST2 = CONST>
enable_if_t<!CONST2, T*> operator->() constexpr enable_if_t<!CONST2, T*> operator->()
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_outer_current != m_outer_end); ASSERT(m_outer_current != m_outer_end);
@ -234,7 +234,7 @@ namespace BAN
return m_inner_current.operator->(); return m_inner_current.operator->();
} }
IteratorDoubleGeneral& operator++() constexpr IteratorDoubleGeneral& operator++()
{ {
ASSERT(*this); ASSERT(*this);
ASSERT(m_outer_current != m_outer_end); ASSERT(m_outer_current != m_outer_end);
@ -243,14 +243,14 @@ namespace BAN
find_valid_or_end(); find_valid_or_end();
return *this; return *this;
} }
IteratorDoubleGeneral operator++(int) constexpr IteratorDoubleGeneral operator++(int)
{ {
auto temp = *this; auto temp = *this;
++(*this); ++(*this);
return temp; return temp;
} }
bool operator==(const IteratorDoubleGeneral& other) const constexpr bool operator==(const IteratorDoubleGeneral& other) const
{ {
ASSERT(*this && other); ASSERT(*this && other);
if (m_outer_end != other.m_outer_end) if (m_outer_end != other.m_outer_end)
@ -262,18 +262,18 @@ namespace BAN
ASSERT(m_inner_current && other.m_inner_current); ASSERT(m_inner_current && other.m_inner_current);
return m_inner_current == other.m_inner_current; return m_inner_current == other.m_inner_current;
} }
bool operator!=(const IteratorDoubleGeneral& other) const constexpr bool operator!=(const IteratorDoubleGeneral& other) const
{ {
return !(*this == other); return !(*this == other);
} }
explicit operator bool() const constexpr explicit operator bool() const
{ {
return !!m_outer_current; return !!m_outer_current;
} }
private: private:
IteratorDoubleGeneral(const OuterIterator& outer_end, const OuterIterator& outer_current) constexpr IteratorDoubleGeneral(const OuterIterator& outer_end, const OuterIterator& outer_current)
: m_outer_end(outer_end) : m_outer_end(outer_end)
, m_outer_current(outer_current) , m_outer_current(outer_current)
{ {
@ -284,7 +284,7 @@ namespace BAN
} }
} }
IteratorDoubleGeneral(const OuterIterator& outer_end, const OuterIterator& outer_current, const InnerIterator& inner_current) constexpr IteratorDoubleGeneral(const OuterIterator& outer_end, const OuterIterator& outer_current, const InnerIterator& inner_current)
: m_outer_end(outer_end) : m_outer_end(outer_end)
, m_outer_current(outer_current) , m_outer_current(outer_current)
, m_inner_current(inner_current) , m_inner_current(inner_current)
@ -292,7 +292,7 @@ namespace BAN
find_valid_or_end(); find_valid_or_end();
} }
void find_valid_or_end() constexpr void find_valid_or_end()
{ {
while (m_inner_current == m_outer_current->end()) while (m_inner_current == m_outer_current->end())
{ {
@ -303,8 +303,8 @@ namespace BAN
} }
} }
OuterIterator outer_current() { return m_outer_current; } constexpr OuterIterator outer_current() { return m_outer_current; }
InnerIterator inner_current() { return m_inner_current; } constexpr InnerIterator inner_current() { return m_inner_current; }
private: private:
OuterIterator m_outer_end; OuterIterator m_outer_end;

View File

@ -13,35 +13,35 @@ namespace BAN
class Optional class Optional
{ {
public: public:
Optional(); constexpr Optional();
Optional(Optional&&); constexpr Optional(Optional&&);
Optional(const Optional&); constexpr Optional(const Optional&);
Optional(const T&); constexpr Optional(const T&);
Optional(T&&); constexpr Optional(T&&);
template<typename... Args> template<typename... Args>
Optional(Args&&...); constexpr Optional(Args&&...);
~Optional(); ~Optional();
Optional& operator=(Optional&&); constexpr Optional& operator=(Optional&&);
Optional& operator=(const Optional&); constexpr Optional& operator=(const Optional&);
template<typename... Args> template<typename... Args>
Optional& emplace(Args&&...); constexpr Optional& emplace(Args&&...);
T* operator->(); constexpr T* operator->();
const T* operator->() const; constexpr const T* operator->() const;
T& operator*(); constexpr T& operator*();
const T& operator*() const; constexpr const T& operator*() const;
bool has_value() const; constexpr bool has_value() const;
T release_value(); constexpr T release_value();
T& value(); constexpr T& value();
const T& value() const; constexpr const T& value() const;
void clear(); constexpr void clear();
private: private:
alignas(T) uint8_t m_storage[sizeof(T)]; alignas(T) uint8_t m_storage[sizeof(T)];
@ -49,12 +49,12 @@ namespace BAN
}; };
template<typename T> template<typename T>
Optional<T>::Optional() constexpr Optional<T>::Optional()
: m_has_value(false) : m_has_value(false)
{} {}
template<typename T> template<typename T>
Optional<T>::Optional(Optional<T>&& other) constexpr Optional<T>::Optional(Optional<T>&& other)
: m_has_value(other.has_value()) : m_has_value(other.has_value())
{ {
if (other.has_value()) if (other.has_value())
@ -62,7 +62,7 @@ namespace BAN
} }
template<typename T> template<typename T>
Optional<T>::Optional(const Optional<T>& other) constexpr Optional<T>::Optional(const Optional<T>& other)
: m_has_value(other.has_value()) : m_has_value(other.has_value())
{ {
if (other.has_value()) if (other.has_value())
@ -70,14 +70,14 @@ namespace BAN
} }
template<typename T> template<typename T>
Optional<T>::Optional(const T& value) constexpr Optional<T>::Optional(const T& value)
: m_has_value(true) : m_has_value(true)
{ {
new (m_storage) T(value); new (m_storage) T(value);
} }
template<typename T> template<typename T>
Optional<T>::Optional(T&& value) constexpr Optional<T>::Optional(T&& value)
: m_has_value(true) : m_has_value(true)
{ {
new (m_storage) T(move(value)); new (m_storage) T(move(value));
@ -85,7 +85,7 @@ namespace BAN
template<typename T> template<typename T>
template<typename... Args> template<typename... Args>
Optional<T>::Optional(Args&&... args) constexpr Optional<T>::Optional(Args&&... args)
: m_has_value(true) : m_has_value(true)
{ {
new (m_storage) T(forward<Args>(args)...); new (m_storage) T(forward<Args>(args)...);
@ -98,7 +98,7 @@ namespace BAN
} }
template<typename T> template<typename T>
Optional<T>& Optional<T>::operator=(Optional&& other) constexpr Optional<T>& Optional<T>::operator=(Optional&& other)
{ {
clear(); clear();
m_has_value = other.has_value(); m_has_value = other.has_value();
@ -108,7 +108,7 @@ namespace BAN
} }
template<typename T> template<typename T>
Optional<T>& Optional<T>::operator=(const Optional& other) constexpr Optional<T>& Optional<T>::operator=(const Optional& other)
{ {
clear(); clear();
m_has_value = other.has_value(); m_has_value = other.has_value();
@ -119,7 +119,7 @@ namespace BAN
template<typename T> template<typename T>
template<typename... Args> template<typename... Args>
Optional<T>& Optional<T>::emplace(Args&&... args) constexpr Optional<T>& Optional<T>::emplace(Args&&... args)
{ {
clear(); clear();
m_has_value = true; m_has_value = true;
@ -128,41 +128,41 @@ namespace BAN
} }
template<typename T> template<typename T>
T* Optional<T>::operator->() constexpr T* Optional<T>::operator->()
{ {
ASSERT(has_value()); ASSERT(has_value());
return &value(); return &value();
} }
template<typename T> template<typename T>
const T* Optional<T>::operator->() const constexpr const T* Optional<T>::operator->() const
{ {
ASSERT(has_value()); ASSERT(has_value());
return &value(); return &value();
} }
template<typename T> template<typename T>
T& Optional<T>::operator*() constexpr T& Optional<T>::operator*()
{ {
ASSERT(has_value()); ASSERT(has_value());
return value(); return value();
} }
template<typename T> template<typename T>
const T& Optional<T>::operator*() const constexpr const T& Optional<T>::operator*() const
{ {
ASSERT(has_value()); ASSERT(has_value());
return value(); return value();
} }
template<typename T> template<typename T>
bool Optional<T>::has_value() const constexpr bool Optional<T>::has_value() const
{ {
return m_has_value; return m_has_value;
} }
template<typename T> template<typename T>
T Optional<T>::release_value() constexpr T Optional<T>::release_value()
{ {
ASSERT(has_value()); ASSERT(has_value());
T released_value = move(value()); T released_value = move(value());
@ -172,21 +172,21 @@ namespace BAN
} }
template<typename T> template<typename T>
T& Optional<T>::value() constexpr T& Optional<T>::value()
{ {
ASSERT(has_value()); ASSERT(has_value());
return (T&)m_storage; return (T&)m_storage;
} }
template<typename T> template<typename T>
const T& Optional<T>::value() const constexpr const T& Optional<T>::value() const
{ {
ASSERT(has_value()); ASSERT(has_value());
return (const T&)m_storage; return (const T&)m_storage;
} }
template<typename T> template<typename T>
void Optional<T>::clear() constexpr void Optional<T>::clear()
{ {
if (m_has_value) if (m_has_value)
value().~T(); value().~T();

View File

@ -16,40 +16,44 @@ namespace BAN
using const_iterator = ConstIteratorSimple<char, StringView>; using const_iterator = ConstIteratorSimple<char, StringView>;
public: public:
StringView() {} constexpr StringView() {}
StringView(const String&); constexpr StringView(const char* string, size_type len = -1)
StringView(const char* string, size_type len = -1)
{ {
if (len == size_type(-1)) if (len == size_type(-1))
len = strlen(string); len = strlen(string);
m_data = string; m_data = string;
m_size = len; m_size = len;
} }
StringView(const String&);
const_iterator begin() const { return const_iterator(m_data); } constexpr const_iterator begin() const { return const_iterator(m_data); }
const_iterator end() const { return const_iterator(m_data + m_size); } constexpr const_iterator end() const { return const_iterator(m_data + m_size); }
char operator[](size_type index) const constexpr char operator[](size_type index) const
{ {
ASSERT(index < m_size); ASSERT(index < m_size);
return m_data[index]; return m_data[index];
} }
bool operator==(StringView other) const constexpr bool operator==(StringView other) const
{ {
if (m_size != other.m_size) if (m_size != other.m_size)
return false; return false;
return memcmp(m_data, other.m_data, m_size) == 0; for (size_type i = 0; i < m_size; i++)
if (m_data[i] != other.m_data[i])
return false;
return true;
} }
bool operator==(const char* other) const constexpr bool operator==(const char* other) const
{ {
if (memcmp(m_data, other, m_size)) for (size_type i = 0; i < m_size; i++)
return false; if (m_data[i] != other[i])
return false;
return other[m_size] == '\0'; return other[m_size] == '\0';
} }
StringView substring(size_type index, size_type len = -1) const constexpr StringView substring(size_type index, size_type len = -1) const
{ {
ASSERT(index <= m_size); ASSERT(index <= m_size);
if (len == size_type(-1)) if (len == size_type(-1))
@ -133,13 +137,13 @@ namespace BAN
return result; return result;
} }
char back() const constexpr char back() const
{ {
ASSERT(m_size > 0); ASSERT(m_size > 0);
return m_data[m_size - 1]; return m_data[m_size - 1];
} }
char front() const constexpr char front() const
{ {
ASSERT(m_size > 0); ASSERT(m_size > 0);
return m_data[0]; return m_data[0];
@ -161,7 +165,7 @@ namespace BAN
return {}; return {};
} }
bool contains(char ch) const constexpr bool contains(char ch) const
{ {
for (size_type i = 0; i < m_size; i++) for (size_type i = 0; i < m_size; i++)
if (m_data[i] == ch) if (m_data[i] == ch)
@ -169,7 +173,7 @@ namespace BAN
return false; return false;
} }
size_type count(char ch) const constexpr size_type count(char ch) const
{ {
size_type result = 0; size_type result = 0;
for (size_type i = 0; i < m_size; i++) for (size_type i = 0; i < m_size; i++)
@ -178,9 +182,9 @@ namespace BAN
return result; return result;
} }
bool empty() const { return m_size == 0; } constexpr bool empty() const { return m_size == 0; }
size_type size() const { return m_size; } constexpr size_type size() const { return m_size; }
const char* data() const { return m_data; } constexpr const char* data() const { return m_data; }
private: private:
const char* m_data = nullptr; const char* m_data = nullptr;
@ -189,7 +193,7 @@ namespace BAN
} }
inline BAN::StringView operator""sv(const char* str, BAN::StringView::size_type len) { return BAN::StringView(str, len); } inline constexpr BAN::StringView operator""sv(const char* str, BAN::StringView::size_type len) { return BAN::StringView(str, len); }
namespace BAN::Formatter namespace BAN::Formatter
{ {