diff options
Diffstat (limited to 'src/common.hpp')
-rw-r--r-- | src/common.hpp | 123 |
1 files changed, 95 insertions, 28 deletions
diff --git a/src/common.hpp b/src/common.hpp index 76940d25..55e0f833 100644 --- a/src/common.hpp +++ b/src/common.hpp @@ -72,26 +72,56 @@ static inline Ordering ord(bool l, bool r) else return OrdLess; } +static inline Ordering ord(char l, char r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} + +static inline Ordering ord(unsigned char l, unsigned char r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} +static inline Ordering ord(unsigned short l, unsigned short r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} static inline Ordering ord(unsigned l, unsigned r) { - if(l == r) - return OrdEqual; - else if( l > r ) - return OrdGreater; - else - return OrdLess; + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); } -#if UINTPTR_MAX != UINT_MAX -static inline Ordering ord(::std::uintptr_t l, ::std::uintptr_t r) +static inline Ordering ord(unsigned long l, unsigned long r) { - if(l == r) - return OrdEqual; - else if( l > r ) - return OrdGreater; - else - return OrdLess; + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); } -#endif +static inline Ordering ord(unsigned long long l, unsigned long long r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} +static inline Ordering ord(signed char l, signed char r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} +static inline Ordering ord(short l, short r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} +static inline Ordering ord(long l, long r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} +static inline Ordering ord(long long l, long long r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} +static inline Ordering ord(float l, float r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} +static inline Ordering ord(double l, double r) +{ + return (l == r ? OrdEqual : (l > r ? OrdGreater : OrdLess)); +} + static inline Ordering ord(const ::std::string& l, const ::std::string& r) { if(l == r) @@ -302,19 +332,8 @@ struct FmtEscaped { FmtEscaped(const ::std::string& s): s(s.c_str()) {} - friend ::std::ostream& operator<<(::std::ostream& os, const FmtEscaped& x) { - for(auto s = x.s; *s != '\0'; s ++) - { - switch(*s) - { - case '\n': os << "\\n"; break; - case '\\': os << "\\\\"; break; - case '"': os << "\\\""; break; - default: os << *s; break; - } - } - return os; - } + // See main.cpp + friend ::std::ostream& operator<<(::std::ostream& os, const FmtEscaped& x); }; // ------------------------------------------------------------------- @@ -333,4 +352,52 @@ auto end (reversion_wrapper<T> w) { return w.iterable.rend(); } template <typename T> reversion_wrapper<T> reverse (T&& iterable) { return { iterable }; } + +template<typename T> +struct RunIterable { + const ::std::vector<T>& list; + unsigned int ofs; + ::std::pair<size_t,size_t> cur; + RunIterable(const ::std::vector<T>& list): + list(list), ofs(0) + { + advance(); + } + void advance() { + if( ofs < list.size() ) + { + auto start = ofs; + while(ofs < list.size() && list[ofs] == list[start]) + ofs ++; + cur = ::std::make_pair(start, ofs-1); + } + else + { + ofs = list.size()+1; + } + } + RunIterable<T> begin() { return *this; } + RunIterable<T> end() { auto rv = *this; rv.ofs = list.size()+1; return rv; } + bool operator==(const RunIterable<T>& x) { + return x.ofs == ofs; + } + bool operator!=(const RunIterable<T>& x) { + return !(*this == x); + } + void operator++() { + advance(); + } + const ::std::pair<size_t,size_t>& operator*() const { + return this->cur; + } + const ::std::pair<size_t,size_t>* operator->() const { + return &this->cur; + } +}; +template<typename T> +RunIterable<T> runs(const ::std::vector<T>& x) { + return RunIterable<T>(x); +} + + #endif |