Files
Convention-CPP/Convention/[Runtime]/Generics/Sequence.hpp

199 lines
5.3 KiB
C++
Raw Normal View History

2025-06-12 14:59:06 +08:00
#pragma once
#ifndef Convention_Runtime_Generics_Sequence_hpp
#define Convention_Runtime_Generics_Sequence_hpp
#include"Config.hpp"
namespace Convention
{
namespace Generics
{
namespace Iterator
2025-06-12 21:46:53 +08:00
{
2025-06-13 21:56:11 +08:00
/**
* @brief
* @tparam ReadValueType
* @version BS 0.0.1
*/
template<typename ReadValueType>
struct ISequenceIterator
{
virtual ~ISequenceIterator() {}
virtual void Next() abstract;
virtual ReadValueType ReadValue() const abstract;
2025-06-13 21:56:11 +08:00
ISequenceIterator& operator++()
{
this->Next();
return *this;
}
virtual bool operator==(const ISequenceIterator& other) const noexcept abstract;
bool operator!=(const ISequenceIterator& other) const noexcept
{
return !(*this == other);
}
ReadValueType operator*() const
{
return ReadValue();
}
};
2025-06-13 21:56:11 +08:00
/**
* @brief
* @tparam Sequence
* @tparam Index , operator++()
* @tparam ReadValueType
* @version BS 0.0.1
*/
template<
typename Sequence,
typename Index,
typename ReadValueType = decltype(std::declval<Sequence>()[std::declval<Index>()])
>
class DefaultSequenceIterator
: public ISequenceIterator<ReadValueType>,
public IComparable<DefaultSequenceIterator<Sequence, Index, ReadValueType>, ICompare<Index>>
{
2025-06-13 21:56:11 +08:00
private:
Sequence& target;
Index index;
public:
2025-06-13 21:56:11 +08:00
operator const Index&()
{
return index;
}
DefaultSequenceIterator(Sequence& target, Index index)
: __init(target), __init(index)
{
}
DefaultSequenceIterator(const DefaultSequenceIterator& other) noexcept
: target(other.target), index(other.index)
{
}
DefaultSequenceIterator& operator=(const DefaultSequenceIterator& other) noexcept
{
target = other.target;
index = other.index;
return *this;
}
virtual ~DefaultSequenceIterator() {}
void Next()
{
index++;
}
ReadValueType ReadValue() const
{
return target[index];
}
bool operator==(const ISequenceIterator<ReadValueType>& other) const noexcept
{
auto ptr = dynamic_cast<const DefaultSequenceIterator* const>(&other);
if (ptr != nullptr)
return index == ptr->index;
return false;
}
};
2025-06-12 21:46:53 +08:00
2025-06-13 21:56:11 +08:00
}
2025-06-12 21:46:53 +08:00
/**
2025-06-13 21:56:11 +08:00
* @brief
* @tparam Element
* @tparam Index , operator++()
* @tparam ReadValueType
2025-06-12 21:46:53 +08:00
* @version BS 0.0.1
*/
2025-06-13 21:56:11 +08:00
template<
typename Element,
typename Index = int,
typename ReadValueType = Element&
>
struct ISequence
2025-06-12 21:46:53 +08:00
{
2025-06-13 21:56:11 +08:00
virtual ~ISequence() {}
virtual ReadValueType operator[](Index index) abstract;
virtual size_t size() const noexcept abstract;
Iterator::ISequenceIterator<ReadValueType> begin() abstract;
Iterator::ISequenceIterator<ReadValueType> end() abstract;
2025-06-12 21:46:53 +08:00
};
/**
* @brief
* @tparam Element
* @tparam size
* @version BS 0.0.1
*/
2025-06-12 14:59:06 +08:00
template<typename Element, size_t size>
using Array = std::array<Element, size>;
2025-06-12 21:46:53 +08:00
/**
* @brief Bool数组
* @tparam size
* @version BS 0.0.1
*/
template<size_t capacity>
class BoolArray
: private Array<
std::conditional_t<PlatformIndicator::IsPlatformx64, int64_t, int32_t>,
capacity / sizeof(std::conditional_t<PlatformIndicator::IsPlatformx64, int64_t, int32_t>) + (capacity % sizeof(std::conditional_t<PlatformIndicator::IsPlatformx64, int64_t, int32_t>) ? 1 : 0)
>
{
private:
constexpr static const char* out_of_range_message = "out of range, capacity: ";
using _MyElementTy = std::conditional_t<PlatformIndicator::IsPlatformx64, int64_t, int32_t>;
constexpr static size_t _MyCapacity = capacity / sizeof(_MyElementTy) + (capacity % sizeof(_MyElementTy) ? 1 : 0);
using _Mybase = Array<_MyElementTy, _MyCapacity>;
constexpr _Mybase& _GetBaseArray() noexcept
{
return *this;
}
constexpr const _Mybase& _GetBaseArray() const noexcept
{
return *this;
}
public:
inline constexpr size_t size() const noexcept
{
return capacity;
}
int ReadValue(size_t index) const
{
if (index < capacity)
{
size_t i = index / sizeof(_MyElementTy), offset = index % sizeof(_MyElementTy);
return _GetBaseArray()[i] & (1ll << offset);
}
throw std::out_of_range(StringIndicator::Combine<std::string>(out_of_range_message, capacity));
}
bool operator[](int index) const
{
return ReadValue(index < 0 ? capacity + index : index);
}
void WriteValue(size_t index, bool value)
{
if (index < capacity)
{
size_t i = index / sizeof(_MyElementTy), offset = index % sizeof(_MyElementTy);
if (value)
_GetBaseArray()[i] |= 1ll << offset;
else
_GetBaseArray()[i] &= ~(1ll << offset);
}
throw std::out_of_range(StringIndicator::Combine<std::string>(out_of_range_message, capacity));
}
};
/**
* @brief
* @tparam Element
* @tparam Allocator
* @version BS 0.0.1
*/
2025-06-12 14:59:06 +08:00
template<typename Element, template<typename> class Allocator>
using Vector = std::vector<Element, Allocator<Element>>;
}
}
2025-06-12 21:46:53 +08:00
#endif Convention_Runtime_Generics_Sequence_hpp