summaryrefslogtreecommitdiff
path: root/src/include/rc_string.hpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/include/rc_string.hpp')
-rw-r--r--src/include/rc_string.hpp81
1 files changed, 64 insertions, 17 deletions
diff --git a/src/include/rc_string.hpp b/src/include/rc_string.hpp
index eec47d80..94b6d9e7 100644
--- a/src/include/rc_string.hpp
+++ b/src/include/rc_string.hpp
@@ -9,38 +9,37 @@
#include <cstring>
#include <ostream>
+#include "../common.hpp"
class RcString
{
unsigned int* m_ptr;
- unsigned int m_len;
public:
RcString():
- m_ptr(nullptr),
- m_len(0)
+ m_ptr(nullptr)
{}
RcString(const char* s, unsigned int len);
RcString(const char* s):
RcString(s, ::std::strlen(s))
{
}
- RcString(const ::std::string& s):
+ explicit RcString(const ::std::string& s):
RcString(s.data(), s.size())
{
}
+ static RcString new_interned(const ::std::string& s);
+ //static new_interned(const char* s);
+
RcString(const RcString& x):
- m_ptr(x.m_ptr),
- m_len(x.m_len)
+ m_ptr(x.m_ptr)
{
if( m_ptr ) *m_ptr += 1;
}
RcString(RcString&& x):
- m_ptr(x.m_ptr),
- m_len(x.m_len)
+ m_ptr(x.m_ptr)
{
x.m_ptr = nullptr;
- x.m_len = 0;
}
~RcString();
@@ -51,7 +50,6 @@ public:
{
this->~RcString();
m_ptr = x.m_ptr;
- m_len = x.m_len;
if( m_ptr ) *m_ptr += 1;
}
return *this;
@@ -62,27 +60,76 @@ public:
{
this->~RcString();
m_ptr = x.m_ptr;
- m_len = x.m_len;
x.m_ptr = nullptr;
- x.m_len = 0;
}
return *this;
}
+ const char* begin() const { return c_str(); }
+ const char* end() const { return c_str() + size(); }
+ size_t size() const { return m_ptr ? m_ptr[1] : 0; }
const char* c_str() const {
- if( m_len > 0 )
+ if( m_ptr )
{
- return reinterpret_cast<const char*>(m_ptr + 1);
+ return reinterpret_cast<const char*>(m_ptr + 2);
}
else
{
return "";
}
}
- bool operator==(const RcString& s) const { return *this == s.c_str(); }
+
+ char back() const {
+ assert(size() > 0 );
+ return *(c_str() + size() - 1);
+ }
+
+ Ordering ord(const RcString& s) const;
+ bool operator==(const RcString& s) const {
+ if(s.size() != this->size())
+ return false;
+ return this->ord(s) == OrdEqual;
+ }
+ bool operator!=(const RcString& s) const {
+ if(s.size() != this->size())
+ return true;
+ return this->ord(s) != OrdEqual;
+ }
+ bool operator<(const RcString& s) const { return this->ord(s) == OrdLess; }
+ bool operator>(const RcString& s) const { return this->ord(s) == OrdGreater; }
+
+ Ordering ord(const std::string& s) const;
+ bool operator==(const std::string& s) const { return this->ord(s) == OrdEqual; }
+ bool operator!=(const std::string& s) const { return this->ord(s) != OrdEqual; }
+ bool operator<(const std::string& s) const { return this->ord(s) == OrdLess; }
+ bool operator>(const std::string& s) const { return this->ord(s) == OrdGreater; }
bool operator==(const char* s) const;
- friend ::std::ostream& operator<<(::std::ostream& os, const RcString& x) {
- return os << x.c_str();
+ bool operator!=(const char* s) const { return !(*this == s); }
+ friend ::std::ostream& operator<<(::std::ostream& os, const RcString& x);
+
+ friend bool operator==(const char* a, const RcString& b) {
+ return b == a;
+ }
+ friend bool operator!=(const char* a, const RcString& b) {
+ return b != a;
+ }
+
+ int compare(size_t o, size_t l, const char* s) const {
+ assert(o <= this->size());
+ return memcmp(this->c_str() + o, s, l);
}
};
+
+namespace std {
+ static inline bool operator==(const string& a, const ::RcString& b) {
+ return b == a;
+ }
+ static inline bool operator!=(const string& a, const ::RcString& b) {
+ return b != a;
+ }
+ template<> struct hash<RcString>
+ {
+ size_t operator()(const RcString& s) const noexcept;
+ };
+}