Attempted a better iterator design but C++ doesn"t make it easy

Fortune for rngxx's current commit: Small blessing − 小吉
iter
Avril 3 years ago
parent 3ff3db0e3e
commit e0518f2115
Signed by: flanchan
GPG Key ID: 284488987C31F630

@ -0,0 +1,62 @@
#pragma once
#include <new>
#include <utility>
namespace rng::util
{
template<typename T>
struct uninit final
{
inline static T* align_buffer(unsigned char* buffer) { return reinterpret_cast<T*>(buffer + alignof(T) - reinterpret_cast<intptr_t>(buffer) % alignof(T)); }
inline static const T* align_buffer(const unsigned char* buffer) { return reinterpret_cast<const T*>(buffer + alignof(T) - reinterpret_cast<intptr_t>(buffer) % alignof(T)); }
inline T* ptr() { return align_buffer(&a_data[0]); }
inline const T* ptr() const { return align_buffer(&a_data[0]); }
inline unsigned char* bytes() { return &a_data[0]; }
inline const unsigned char* bytes() const { return &a_data[0]; }
inline uninit(T&& value) { give(std::move(value)); }
inline uninit(){}
inline void drop() { ptr()->~T(); }
inline T&& take() { return std::move(*ptr()); }
inline void give(T&& value) { new (ptr()) T(std::move(value)); }
inline T& operator=(T&& value) { give(std::move(value)); return *ptr(); }
inline T replace(T&& value) {
auto x = take();
drop();
give(std::move(value));
return x;
}
inline static uninit<T> move(uninit<T>&& m) { return uninit<T>(std::move(m)); }
inline static uninit<T> copy(const uninit<T>& c) { return uninit<T>(c); }
inline uninit<T> bitwise_copy() const {
uninit u;
u.a_data = a_data;
return u;
}
private:
inline uninit(const uninit<T>& copy) : uninit(T(*copy.ptr())){}
inline uninit(uninit<T>&& move) : uninit(std::move(*move.ptr())){}
std::array<unsigned char, sizeof(T)+alignof(T)> a_data;
};
template<typename T>
struct generic_iterator
{
inline T try_next()
{
uninit<T> v;
if(next(v)) { return v.take(); }
else throw "c++ sucks"; //XXX: eh... this is too draining
}
protected:
virtual bool next(uninit<T>& output) = 0;
};
}

@ -1,4 +1,11 @@
#include <rngxx.hpp>
#include <iter.h>
void d(rng::util::generic_iterator<int>& i)
{
i.try_next();
}
//XXX: Doing this is not going to work ...
#if 0

Loading…
Cancel
Save