From 967be9e750221ab2ab783f95df79bb26d290a45e Mon Sep 17 00:00:00 2001 From: Martial Simon Date: Mon, 15 Sep 2025 01:07:58 +0200 Subject: add: added projects --- tiger-compiler/lib/misc/set.hxx | 208 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 208 insertions(+) create mode 100644 tiger-compiler/lib/misc/set.hxx (limited to 'tiger-compiler/lib/misc/set.hxx') diff --git a/tiger-compiler/lib/misc/set.hxx b/tiger-compiler/lib/misc/set.hxx new file mode 100644 index 0000000..9645c95 --- /dev/null +++ b/tiger-compiler/lib/misc/set.hxx @@ -0,0 +1,208 @@ +/** + ** \file misc/set.hxx + ** \brief misc::set: wrapper around std::set. + **/ + +#pragma once + +#include +#include + +#include +#include + +namespace misc +{ + template + template + requires Iterator + inline set::set(Iter first, Iter last) + { + this->insert(first, last); + } + + /* Useful to convert a std::vector or other Compare in misc::set. */ + template + template + requires ConstIterableType + inline set::set(const Container v) + { + for (const Key& x : v) + this->insert(x); + } + + template + inline bool set::has(const Key& k) const + { + return set_type::find(k) != this->end(); + } + + /* \brief Return the addition of \a data into \a this. + \a data must not yet be part of \a this. */ + template + inline set + set::operator+(const Key& data) const + { + precondition(!(data % *this)); + set res(*this); + res.insert(data); + return res; + } + + /* \brief Insert \a data in \a this. + \a data must not yet be part of \a this. */ + template + inline set& + set::operator+=(const Key& data) + { + precondition(!(data % *this)); + this->insert(data); + return *this; + } + + /* \brief Return the removal of \a data into \a this. + \a data must be part of \a this. */ + template + inline set + set::operator-(const Key& data) const + { + precondition(data % *this); + set res(*this); + res.erase(data); + return res; + } + + /* \brief Remove \a data from \a this. + \a data must be part of \a this. */ + template + inline set& + set::operator-=(const Key& data) + { + precondition(data % *this); + this->erase(data); + return *this; + } + + // Union with another set \a s. + // FIXME: Deprecate this use, it ought to be direct sum. + template + inline set set::operator+( + const set& s) const + { + return set_union(*this, s); + } + + // In place union with another set \a s. + template + inline set& set::operator+=( + const set& s) + { + return *this = *this + s; + } + + // Subtraction with another set \a s. + template + inline set set::operator-( + const set& s) const + { + return set_difference(*this, s); + } + + // In place subtraction with another set \a s. + template + inline set& set::operator-=( + const set& s) + { + *this = *this - s; + return *this; + } + + // Union with another set \a s. + template + inline set set::operator|( + const set& s) const + { + return *this + s; + } + + // In place union with another set \a s. + template + inline set& set::operator|=( + const set& s) + { + return *this += s; + } + + // Intersection with another set \a s. + template + inline set set::operator&( + const set& s) const + { + return set_intersection(*this, s); + } + + // In place intersection with another set \a s. + template + inline set& set::operator&=( + const set& s) + { + return *this = *this & s; + } + + template + inline set + set_difference(const set& s1, + const set& s2) + { + set res; + // Specifying the key_comp to use is required: without it, the + // first set is properly ordered using its own key_comp, but + // neither the second set nor the resulting set are ordering + // using it. Even if s1, s2, and res do use the same Compare! + std::set_difference(s1.begin(), s1.end(), s2.begin(), s2.end(), + inserter(res, res.begin()), s1.key_comp()); + return res; + } + + template + inline set + set_intersection(const set& s1, + const set& s2) + { + set res; + std::set_intersection(s1.begin(), s1.end(), s2.begin(), s2.end(), + inserter(res, res.begin()), s1.key_comp()); + return res; + } + + template + inline set + set_union(const set& s1, + const set& s2) + { + set res; + std::set_union(s1.begin(), s1.end(), s2.begin(), s2.end(), + inserter(res, res.begin()), s1.key_comp()); + return res; + } + + template + inline std::ostream& operator<<(std::ostream& ostr, + const set& s) + { + for (auto i = s.begin(); i != s.end();) + { + ostr << *i; + if (++i != s.end()) + ostr << ", "; + } + return ostr; + } + + template + inline bool operator%(const Key& k, const set& s) + { + return s.has(k); + } + +} // namespace misc -- cgit v1.2.3