from_string, constexpr, & others

This commit is contained in:
Marius Bancila 2018-06-29 09:54:51 +03:00
parent a296a1359f
commit 52587059aa
2 changed files with 32 additions and 33 deletions

View File

@ -15,19 +15,20 @@ Original UUID library paper with motivation, specification, and examples.
### 1.2 P0959R1
Revised with feedback from the LWG and the community.
* Removed string constructors and replaced with free overloaded function `from_string()`.
* Removed string constructors and replaced with an overloaded static member function `from_string()`.
* Parsing strings to `uuid` throws exception `uuid_error` instead of creating a nil uuid when the operation fails.
* {} included in the supported format for string parsing, i.e. `"{xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx}"`.
* Removed `state_size`.
* Rename member function `nil()` to `is_nil()`.
* The default constructor is defaulted.
* Added a conversion construct from `std::span<std::byte, 16>`.
* Added the free function `as_bytes()` to convert the `uuid` into a view of its underlying bytes.
* Added the member function `as_bytes()` to convert the `uuid` into a view of its underlying bytes.
* Constructing a `uuid` from a range with a size other than 16 is undefined behaviour.
* Removed mutable iterators (but preserved the constant iterators).
* Removed typedefs and others container-like parts.
* Defined the correlation between the internal UUID bytes and the string representation.
* Added UUID layout and byte order specification from the RFC 4122 document.
# Most functions are constexpr.
## II. Motivation
@ -123,7 +124,7 @@ A nil UUID is a special UUID that has all the bits set to 0. Its canonical textu
uuid id;
assert(id.is_nil());
uuid id = from_string("00000000-0000-0000-0000-000000000000");
uuid id = uuid::from_string("00000000-0000-0000-0000-000000000000");
assert(id.is_nil());
```
@ -202,13 +203,13 @@ assert(!id.is_nil());
### string parsing
Non-member overloaded function `from_string()` allow to create `uuid` instances from various strings.
Static overloaded member function `from_string()` allows to create `uuid` instances from various strings.
The input argument must have the form `xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx` or `{xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx}` where `x` is a hexadecimal digit. Should the argument be of a different format, an `uuid_error` exception is thrown.
```cpp
auto id1 = from_string("47183823-2574-4bfd-b411-99ed177d3e43");
auto id2 = from_string(L"{47183823-2574-4bfd-b411-99ed177d3e43}");
auto id1 = uuid::from_string("47183823-2574-4bfd-b411-99ed177d3e43");
auto id2 = uuid::from_string(L"{47183823-2574-4bfd-b411-99ed177d3e43}");
```
The order of the bytes in the input string reflects directly into the internal representation of the UUID. That is, for an input string in the form `"aabbccdd-eeff-gghh-iijj-kkllmmnnoopp"` or `"{aabbccdd-eeff-gghh-iijj-kkllmmnnoopp}"` the internal byte order of the resulted UUID is `aa,bb,cc,dd,ee,ff,gg,hh,ii,jj,kk,ll,mm,nn,oo,pp`.
@ -403,32 +404,36 @@ namespace std {
namespace std {
struct uuid
{
typedef uint8_t value_type;
typedef /*implementation-defined*/ const_iterator;
using value_type = uint8_t;
using const_iterator = /*implementation-defined*/;
constexpr uuid() noexcept = default;
explicit uuid(std::span<value_type, 16> bytes);
constexpr explicit uuid(std::span<value_type, 16> bytes);
template<typename ForwardIterator>
explicit uuid(ForwardIterator first, ForwardIterator last);
constexpr explicit uuid(ForwardIterator first, ForwardIterator last);
constexpr uuid_variant variant() const noexcept;
constexpr uuid_version version() const noexcept;
constexpr std::size_t size() const noexcept;
constexpr bool is_nil() const noexcept;
void swap(uuid & other) noexcept;
constexpr void swap(uuid & other) noexcept;
const_iterator begin() const noexcept;
const_iterator end() const noexcept;
constexpr const_iterator begin() const noexcept;
constexpr const_iterator end() const noexcept;
std::span<std::byte, 16> as_bytes();
std::span<std::byte const, 16> as_bytes() const;
constexpr std::span<std::byte const, 16> as_bytes() const;
template <typename TChar>
static uuid from_string(TChar const * const str, size_t const size);
static uuid from_string(std::string_view str);
static uuid from_string(std::wstring_view str);
private:
friend bool operator==(uuid const & lhs, uuid const & rhs) noexcept;
friend bool operator<(uuid const & lhs, uuid const & rhs) noexcept;
friend constexpr bool operator==(uuid const & lhs, uuid const & rhs) noexcept;
friend constexpr bool operator<(uuid const & lhs, uuid const & rhs) noexcept;
template <class Elem, class Traits>
friend std::basic_ostream<Elem, Traits> & operator<<(std::basic_ostream<Elem, Traits> &s, uuid const & id);
@ -440,24 +445,17 @@ namespace std {
```cpp
namespace std {
inline bool operator== (uuid const& lhs, uuid const& rhs) noexcept;
inline bool operator!= (uuid const& lhs, uuid const& rhs) noexcept;
inline bool operator< (uuid const& lhs, uuid const& rhs) noexcept;
inline constexpr bool operator== (uuid const& lhs, uuid const& rhs) noexcept;
inline constexpr bool operator!= (uuid const& lhs, uuid const& rhs) noexcept;
inline constexpr bool operator< (uuid const& lhs, uuid const& rhs) noexcept;
inline void swap(uuid & lhs, uuid & rhs);
inline constexpr void swap(uuid & lhs, uuid & rhs);
template <class Elem, class Traits>
std::basic_ostream<Elem, Traits> & operator<<(std::basic_ostream<Elem, Traits> &s, uuid const & id);
inline std::string to_string(uuid const & id);
inline std::wstring to_wstring(uuid const & id);
template <typename TChar>
inline uuid from_string(TChar const * const str, size_t const size);
inline uuid from_string(std::string_view str);
inline uuid from_string(std::wstring_view str);
inline std::span<uuid::value_type, 16> as_bytes(uuid id);
inline std::wstring to_wstring(uuid const & id);
}
```

View File

@ -15,6 +15,7 @@ Basic types:
| `uuid` | a class representing a UUID; this can be default constructed (a nil UUID), constructed from a range (defined by a pair of iterators), or from a string. |
| `uuid_variant` | a strongly type enum representing the type of a UUID |
| `uuid_version` | a strongly type enum representing the version of a UUID |
| `uuid_error` | a class representing an exception type for `uuid` operations |
Generators:
@ -109,12 +110,12 @@ assert(id.variant() == uuids::uuid_variant::rfc);
using namespace std::string_literals;
auto str = "47183823-2574-4bfd-b411-99ed177d3e43"s;
uuid id(from_string(str));
uuid id(uuids::uuid::from_string(str));
assert(uuids::to_string(id) == str);
// or
uuid id(from_string(L"{47183823-2574-4bfd-b411-99ed177d3e43}"s));
uuid id(uuids::uuid::from_string(L"{47183823-2574-4bfd-b411-99ed177d3e43}"s));
assert(id.wstring() == str);
```
@ -221,7 +222,7 @@ assert(ids.find(uuid{}) != ids.end());
```cpp
using namespace std::string_literals;
auto str = "47183823-2574-4bfd-b411-99ed177d3e43"s;
uuid id(from_string(str));
uuid id(uuids::uuid::from_string(str));
auto h1 = std::hash<std::string>{};
auto h2 = std::hash<uuid>{};