| @ -0,0 +1 @@ | |||||
| test | |||||
| @ -0,0 +1,6 @@ | |||||
| all: test | |||||
| test: | |||||
| g++ -Iinclude --std=c++17 -o test tests/*.cpp | |||||
| @ -0,0 +1,2 @@ | |||||
| #pragma once | |||||
| #include "combinations/all.hpp" | |||||
| @ -0,0 +1,5 @@ | |||||
| #pragma once | |||||
| #include "combinations/function.hpp" | |||||
| #include "combinations/compose.hpp" | |||||
| #include "combinations/tuple.hpp" | |||||
| #include "combinations/curry.hpp" | |||||
| @ -0,0 +1,47 @@ | |||||
| #pragma once | |||||
| #include "combinations/tuple.hpp" | |||||
| namespace cl{ | |||||
| struct sigil_t{ | |||||
| constexpr sigil_t(){} | |||||
| }; | |||||
| sigil_t sigil; | |||||
| template<typename a, typename ...c> | |||||
| class compose{ | |||||
| // f . next | |||||
| a f; | |||||
| compose<c...> next; | |||||
| public: | |||||
| compose(a fn1, c ...oth) | |||||
| : f{fn1} | |||||
| , next{oth...} | |||||
| {} | |||||
| template<typename ...t> | |||||
| auto operator()(t ...Args){ | |||||
| return next(f(Args...)); | |||||
| } | |||||
| }; | |||||
| template<typename a> | |||||
| class compose<a>{ | |||||
| // f . g | |||||
| a f; | |||||
| public: | |||||
| compose(a fn1) | |||||
| : f{fn1} | |||||
| {} | |||||
| template<typename ...t> | |||||
| auto operator()(t ...Args){ | |||||
| return f(Args...); | |||||
| } | |||||
| }; | |||||
| template<typename a, typename b> | |||||
| auto operator*(a fn1, b fn2) | |||||
| { | |||||
| return compose(fn1, fn2); | |||||
| } | |||||
| } | |||||
| @ -0,0 +1,20 @@ | |||||
| #pragma once | |||||
| namespace cl | |||||
| { | |||||
| template<typename a, typename fn> | |||||
| class curry | |||||
| { | |||||
| a param; | |||||
| fn call; | |||||
| public: | |||||
| curry(a p, fn func) | |||||
| : param{p} | |||||
| , call{func} | |||||
| {} | |||||
| template<typename ...b> | |||||
| auto operator()(b ...Args){ | |||||
| return call(param, Args...); | |||||
| } | |||||
| }; | |||||
| } | |||||
| @ -0,0 +1,28 @@ | |||||
| #pragma once | |||||
| #include "combinations/curry.hpp" | |||||
| namespace cl | |||||
| { | |||||
| template <typename a> | |||||
| class function{ | |||||
| a me; | |||||
| public: | |||||
| function(a value) | |||||
| : me(value) | |||||
| {} | |||||
| template<typename ...b> | |||||
| auto operator()(b ...Args){ | |||||
| return me(Args...); | |||||
| } | |||||
| template<typename cur, typename ...b> | |||||
| auto operator()(cur arg){ | |||||
| return curry(arg, me); | |||||
| } | |||||
| }; | |||||
| template<typename invokable, typename ret, typename ...Args> | |||||
| ret invoke(invokable fn, Args ...args) | |||||
| { | |||||
| return fn(args...); | |||||
| } | |||||
| } | |||||
| @ -0,0 +1,28 @@ | |||||
| #pragma once | |||||
| #include <stddef.h> | |||||
| namespace cl | |||||
| { | |||||
| template<typename a, typename ...b> | |||||
| class tuple{ | |||||
| a _mine; | |||||
| tuple<b...> _child; | |||||
| template<size_t idx, a, b...> | |||||
| friend a get(); | |||||
| public: | |||||
| tuple(a mine, b ...child) | |||||
| : _mine(mine) | |||||
| , _child(child...) | |||||
| {} | |||||
| }; | |||||
| template<size_t idx, typename ...a> | |||||
| constexpr auto get(tuple<a...> v) | |||||
| { | |||||
| if constexpr (idx!=0) | |||||
| return get<idx-1>(v._child); | |||||
| else | |||||
| return v._mine; | |||||
| } | |||||
| } | |||||
| @ -0,0 +1,15 @@ | |||||
| #include "2CL.hpp" | |||||
| #include <assert.h> | |||||
| struct test_001{ | |||||
| test_001() | |||||
| { | |||||
| auto fn = cl::compose( | |||||
| [](int a)->int{return a+2;}, | |||||
| [](int a)->int{return a*2;} | |||||
| ); | |||||
| assert(fn(1)==6); | |||||
| } | |||||
| }; | |||||
| test_001 run_001; | |||||
| @ -0,0 +1,4 @@ | |||||
| int main() | |||||
| { | |||||
| return 0; | |||||
| } | |||||