100 lines
2.9 KiB
C
100 lines
2.9 KiB
C
|
#ifndef ALSK_ALSK_EDSL_OP_IMPL_ITERSEL_H
|
||
|
#define ALSK_ALSK_EDSL_OP_IMPL_ITERSEL_H
|
||
|
|
||
|
#include <utility>
|
||
|
|
||
|
#include "../traits.h"
|
||
|
#include "../../../skeleton/bone/itersel.h"
|
||
|
#include "../../../skeleton/struct/struct.h"
|
||
|
#include "../../../skeleton/link/link.h"
|
||
|
|
||
|
namespace alsk {
|
||
|
namespace edsl {
|
||
|
|
||
|
template<typename, typename> struct Loop;
|
||
|
template<typename, typename, typename> struct FarmSel;
|
||
|
|
||
|
template<typename Signature_, typename Task, typename Select>
|
||
|
struct IterSel: OperandBase {
|
||
|
Task task;
|
||
|
Select select;
|
||
|
unsigned int n;
|
||
|
|
||
|
constexpr IterSel(Task task, Select select, unsigned int n)
|
||
|
noexcept(noexcept(Task{std::move(task)}) and noexcept(Select{std::move(select)})):
|
||
|
task{std::move(task)}, select{std::move(select)}, n{n}
|
||
|
{}
|
||
|
|
||
|
template<typename S>
|
||
|
constexpr IterSel(IterSel<S, Task, Select> const& o)
|
||
|
noexcept(noexcept(Task{o.task}) and noexcept(Select{o.select})):
|
||
|
task{o.task}, select{o.select}, n{o.n}
|
||
|
{}
|
||
|
|
||
|
template<typename S>
|
||
|
constexpr IterSel(IterSel<S, Task, Select>&& o)
|
||
|
noexcept(noexcept(Task{std::move(o.task)}) and noexcept(Select{std::move(o.select)})):
|
||
|
task{std::move(o.task)}, select{std::move(o.select)}, n{std::move(o.n)}
|
||
|
{}
|
||
|
|
||
|
using Signature = Signature_;
|
||
|
|
||
|
using Struct = S<alsk::IterSel, typename Task::Struct, typename Select::Struct>;
|
||
|
using Links = L<alsk::IterSel, Signature, typename Task::Links, typename Select::Links>;
|
||
|
|
||
|
template<typename S>
|
||
|
constexpr void setup(S& skeleton) const {
|
||
|
skeleton.n = n;
|
||
|
setupFor(task, skeleton.task);
|
||
|
setupFor(select, skeleton.select);
|
||
|
}
|
||
|
|
||
|
template<typename Signature>
|
||
|
constexpr auto link() const&& {
|
||
|
return IterSel<Signature, Task, Select>{std::move(*this)};
|
||
|
}
|
||
|
|
||
|
template<typename Signature>
|
||
|
constexpr auto link() const& {
|
||
|
return IterSel<Signature, Task, Select>{*this};
|
||
|
}
|
||
|
};
|
||
|
|
||
|
namespace impl {
|
||
|
|
||
|
template<typename, typename> struct Iter;
|
||
|
|
||
|
template<typename Task, typename R, typename... Args>
|
||
|
struct Iter<Task, R(Args...)> {
|
||
|
Task const& task;
|
||
|
unsigned int n;
|
||
|
|
||
|
template<typename Select, std::enable_if_t<isOperand<Select>>* = nullptr>
|
||
|
constexpr auto select(Select const& select) {
|
||
|
using Signature = GetReturnType<Select>(Args...);
|
||
|
return alsk::edsl::IterSel<Signature, Task, Select>{task, select, n};
|
||
|
}
|
||
|
};
|
||
|
|
||
|
}
|
||
|
|
||
|
template<typename Signature = void(), typename Task, std::enable_if_t<isOperand<Task>>* = nullptr>
|
||
|
constexpr auto iter(Task const& task, unsigned int n = 0) {
|
||
|
return impl::Iter<Task, Signature>{task, n};
|
||
|
}
|
||
|
|
||
|
template<typename Signature, typename Task, typename Select>
|
||
|
constexpr auto operator&(FarmSel<Signature, Task, Select> const& farmsel) {
|
||
|
return IterSel<Signature, Task, Select>{farmsel.task, farmsel.select, farmsel.n};
|
||
|
}
|
||
|
|
||
|
template<typename LR, typename... LArgs, typename Task, typename Rhs, std::enable_if_t<isOperand<Rhs>>* = nullptr>
|
||
|
constexpr auto operator->*(Loop<LR(LArgs...), Task> const& loop, Rhs const& rhs) {
|
||
|
return IterSel<GetReturnType<Rhs>(LArgs...), Task, Rhs>{loop.task, rhs, loop.n};
|
||
|
}
|
||
|
|
||
|
}
|
||
|
}
|
||
|
|
||
|
#endif
|