Last active
November 25, 2016 16:33
-
-
Save MizukiSonoko/01cf205384647efb2dee23a3cfaccae9 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <iostream> | |
#include <functional> | |
#include <algorithm> | |
#include <vector> | |
#include <list> | |
#include <array> | |
#include <string> | |
#include <initializer_list> | |
using std::cout; | |
using std::endl; | |
template<typename T> | |
using function = std::function<T>; | |
template<class T> | |
struct List : public std::vector<T>{ | |
List(long long len): | |
std::vector<T>(len) | |
{} | |
List(std::initializer_list<T> al): | |
std::vector<T>(al) | |
{} | |
List& map(const function<T(T)>& f){ | |
std::transform( this->begin(), this->end(), this->begin(), f); | |
return *this; | |
} | |
List& filter(const function<bool(T)>& f){ | |
for(auto& v: *this){ | |
if(!f(v)){ | |
this->erase(std::remove( this->begin(), this->end(), v), this->end()); | |
} | |
} | |
return *this; | |
} | |
void zipWithIndex(const function<void(T,int)>&& f){ | |
size_t position = 0; | |
for(auto&& v: *this){ | |
f( v, position); | |
position++; | |
} | |
} | |
T reduce_impl(const function<T(T,T)>& f,const T& v1, const T& v2, List<T>* list){ | |
if(list->empty()){ | |
return f( v1, v2); | |
}else{ | |
auto top = *list->begin(); | |
list->erase(this->begin()); | |
return reduce_impl( f, f( v1, v2), top, list); | |
} | |
} | |
T reduce(const function<T(T,T)>&& f){ | |
if(this->size() >= 2){ | |
auto v1 = this->at(0);auto v2 = this->at(1); | |
this->erase(this->begin());this->erase(this->begin()); | |
return reduce_impl( f, v1, v2, this); | |
}else{ | |
return this->at(0); | |
} | |
} | |
void foreach(const function<void(T)>& f){ | |
for(const auto& v: *this){ | |
f(v); | |
} | |
} | |
auto stringify(T&& t) { | |
return std::to_string(std::forward<T>(t)); | |
} | |
std::string mkString_impl(const std::string& cur,const std::string& interval,typename std::vector<T>::iterator it){ | |
++it; | |
if(it == this->end()){ | |
return cur; | |
}else{ | |
return mkString_impl(cur+interval+stringify(std::move(*it)),interval, it); | |
} | |
} | |
std::string mkString(const std::string& interval){ | |
return mkString_impl( stringify(std::move(*this->begin())), interval, this->begin()); | |
} | |
}; | |
template<typename T> | |
auto L(const std::initializer_list<T>& iniList) -> List<T>{ | |
return List<T>(iniList); | |
} | |
template<typename T, typename... Args> | |
auto L(T const& head, Args... tail) { | |
return List<T>({head, tail...}); | |
} | |
template<typename T> | |
using l = List<T>; | |
struct Generator{ | |
int value; | |
Generator(int v):value(v-1){} | |
auto operator ()(const long long& last,const unsigned long long& step = 1){ | |
List<int> v(std::abs(value-last)/step); | |
std::generate(v.begin(), v.end(), [&number = value,value = value,last,step](){ | |
if(value - last < 0) { | |
return number += step; | |
}else{ | |
return number -= step; | |
} | |
}); | |
return v; | |
} | |
}; | |
Generator operator"" _to (unsigned long long n){ | |
return Generator(n); | |
} | |
int main(){ | |
l<int>{ 1, 2, 3, 4, 5} | |
.map([](auto v){ return v + 1;}) | |
.filter([](auto v)-> bool{ return v % 2;}) | |
.foreach([](auto v){ | |
cout << v <<" "<< endl; | |
}); | |
auto sum = l<int>{ 1, 2, 3, 4, 5} | |
.reduce([](auto a,auto b){ return a + b; }); | |
cout <<"sum is "<< sum <<endl; | |
cout <<"sum is "<< 1_to(5).reduce([](auto a,auto b){ return a + b; }) << endl; | |
auto mul = l<int>{ 1, 2, 3, 4, 5} | |
.reduce([](auto a,auto b){ return a * b; }); | |
cout <<"mul is "<< mul <<endl; | |
cout <<"mul is "<< 1_to(5).reduce([](auto a,auto b){ return a * b; }) << endl; | |
auto str = l<int>{ 1, 2, 3, 4, 5} | |
.mkString(", "); | |
cout <<"mkString is "<< str << endl; | |
cout <<"mkString is "<< 1_to(5).mkString(", ") << endl; | |
l<double>{ 1.0, 2.0, 3.0, 4.0, 5.0} | |
.zipWithIndex([](auto v,int p){ | |
cout<<"zipWithIndex array["<< p <<"]= "<< v <<endl; | |
}); | |
0_to(10) | |
.foreach([](auto v){ | |
cout <<"foreach "<< v <<" "<< endl; | |
}); | |
l<int>{ 1, 2, 3, 4, 5} | |
.filter([](auto i){ | |
cout<<"fitler "<< i << endl; | |
return i % 2 == 0; | |
}).map([](auto i){ | |
cout<<"map "<< i << endl; | |
return i * 2; | |
}); | |
return 0; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
~% ./a.out 3 5 sum is 15 sum is 15 mul is 120 mul is 120 mkString is 1, 2, 3, 4, 5 mkString is 1, 2, 3, 4, 5 zipWithIndex array[0]= 1 zipWithIndex array[1]= 2 zipWithIndex array[2]= 3 zipWithIndex array[3]= 4 zipWithIndex array[4]= 5 foreach 0 foreach 1 foreach 2 foreach 3 foreach 4 foreach 5 foreach 6 foreach 7 foreach 8 foreach 9 foreach 10 fitler 1 fitler 3 fitler 5 fitler 5 fitler 5 map 2 map 4