ClearScript/ClearScriptV8/StdString.h

249 строки
7.7 KiB
C++

// Copyright (c) Microsoft Corporation. All rights reserved.
// Licensed under the MIT license.
#pragma once
//-----------------------------------------------------------------------------
// StdChar
//-----------------------------------------------------------------------------
using StdChar = char16_t;
static_assert(sizeof(StdChar) == sizeof(uint16_t));
//-----------------------------------------------------------------------------
// StdString
//-----------------------------------------------------------------------------
class StdString final
{
//-------------------------------------------------------------------------
// types
//-------------------------------------------------------------------------
using Value = std::basic_string<StdChar>;
using UTF8Converter = std::wstring_convert<std::codecvt_utf8_utf16<StdChar>, StdChar>;
public:
//-------------------------------------------------------------------------
// constructors
//-------------------------------------------------------------------------
StdString()
{
}
StdString(const StdString& that):
m_Value(that.m_Value)
{
}
StdString(StdString&& that) noexcept:
m_Value(std::move(that.m_Value))
{
}
explicit StdString(const Value& value):
m_Value(value)
{
}
explicit StdString(Value&& value):
m_Value(std::move(value))
{
}
explicit StdString(const StdChar* pValue):
m_Value(EnsureNonNull(pValue))
{
}
StdString(const StdChar* pValue, int32_t length):
StdString(Value(EnsureNonNull(pValue), length))
{
}
explicit StdString(const std::string& value):
m_Value(UTF8Converter().from_bytes(value))
{
}
//-------------------------------------------------------------------------
// assignment
//-------------------------------------------------------------------------
const StdString& operator=(const StdString& that)
{
m_Value = that.m_Value;
return *this;
}
const StdString& operator=(StdString&& that) noexcept
{
m_Value = std::move(that.m_Value);
return *this;
}
const StdString& operator=(const Value& value)
{
m_Value = value;
return *this;
}
const StdString& operator=(Value&& value)
{
m_Value = std::move(value);
return *this;
}
const StdString& operator=(const StdChar* pValue)
{
m_Value = EnsureNonNull(pValue);
return *this;
}
//-------------------------------------------------------------------------
// concatenation
//-------------------------------------------------------------------------
const StdString& operator+=(const StdString& that)
{
m_Value += that.m_Value;
return *this;
}
const StdString& operator+=(const Value& value)
{
m_Value += value;
return *this;
}
const StdString& operator+=(const StdChar* pValue)
{
m_Value += EnsureNonNull(pValue);
return *this;
}
const StdString& operator+=(StdChar value)
{
m_Value += value;
return *this;
}
//-------------------------------------------------------------------------
// comparison
//-------------------------------------------------------------------------
int Compare(const StdString& that) const { return m_Value.compare(that.m_Value); }
int Compare(const Value& value) const { return m_Value.compare(value); }
int Compare(const StdChar* pValue) const { return m_Value.compare(pValue); }
bool operator==(const StdString& that) const { return m_Value == that.m_Value; }
bool operator==(const Value& value) const { return m_Value == value; }
bool operator==(const StdChar* pValue) const { return m_Value == pValue; }
bool operator!=(const StdString& that) const { return m_Value != that.m_Value; }
bool operator!=(const Value& value) const { return m_Value != value; }
bool operator!=(const StdChar* pValue) const { return m_Value != pValue; }
bool operator<(const StdString& that) const { return m_Value < that.m_Value; }
bool operator<(const Value& value) const { return m_Value < value; }
bool operator<(const StdChar* pValue) const { return m_Value < pValue; }
bool operator<=(const StdString& that) const { return m_Value <= that.m_Value; }
bool operator<=(const Value& value) const { return m_Value <= value; }
bool operator<=(const StdChar* pValue) const { return m_Value <= pValue; }
bool operator>(const StdString& that) const { return m_Value > that.m_Value; }
bool operator>(const Value& value) const { return m_Value > value; }
bool operator>(const StdChar* pValue) const { return m_Value > pValue; }
bool operator>=(const StdString& that) const { return m_Value >= that.m_Value; }
bool operator>=(const Value& value) const { return m_Value >= value; }
bool operator>=(const StdChar* pValue) const { return m_Value >= pValue; }
//-------------------------------------------------------------------------
// miscellaneous
//-------------------------------------------------------------------------
int GetLength() const
{
return static_cast<int>(m_Value.length());
}
size_t GetDigest() const;
const StdChar* ToCString() const
{
return m_Value.c_str();
}
std::string ToUTF8() const
{
return UTF8Converter().to_bytes(m_Value);
}
//-------------------------------------------------------------------------
// V8 extensions
//-------------------------------------------------------------------------
StdString(v8::Isolate* pIsolate, v8::Local<v8::Value> hValue):
m_Value(GetValue(pIsolate, hValue))
{
}
explicit StdString(const v8_inspector::StringView& stringView):
m_Value(GetValue(stringView))
{
}
v8::MaybeLocal<v8::String> ToV8String(v8::Isolate* pIsolate, v8::NewStringType type) const
{
return v8::String::NewFromTwoByte(pIsolate, reinterpret_cast<const uint16_t*>(ToCString()), type, GetLength());
}
v8_inspector::StringView GetStringView(size_t index = 0, size_t length = SIZE_MAX) const
{
auto valueLength = m_Value.length();
index = std::min(index, valueLength);
length = std::min(length, valueLength - index);
return v8_inspector::StringView(reinterpret_cast<const uint16_t*>(ToCString() + index), length);
}
private:
//-------------------------------------------------------------------------
// internals
//-------------------------------------------------------------------------
uint32_t GetDigestAsUInt32() const;
uint64_t GetDigestAsUInt64() const;
static Value GetValue(v8::Isolate* pIsolate, v8::Local<v8::Value> hValue)
{
v8::String::Value value(pIsolate, hValue);
return Value(EnsureNonNull(reinterpret_cast<const StdChar*>(*value)), value.length());
}
static Value GetValue(const v8_inspector::StringView& stringView);
static const StdChar* EnsureNonNull(const StdChar* pValue);
Value m_Value;
};
//-----------------------------------------------------------------------------
// string and character literal support
//-----------------------------------------------------------------------------
#define UTF8_LITERAL(LITERAL) (u ## LITERAL)
#define SL(LITERAL) UTF8_LITERAL(LITERAL)
//-----------------------------------------------------------------------------
// StdString implementation
//-----------------------------------------------------------------------------
inline const StdChar* StdString::EnsureNonNull(const StdChar* pValue)
{
return (pValue != nullptr) ? pValue : SL("");
}