File: Oct.hpp

package info (click to toggle)
reflect-cpp 0.18.0%2Bds-3
  • links: PTS, VCS
  • area: main
  • in suites: trixie
  • size: 12,524 kB
  • sloc: cpp: 44,484; python: 131; makefile: 30; sh: 3
file content (130 lines) | stat: -rw-r--r-- 3,343 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
#ifndef RFL_OCT_HPP_
#define RFL_OCT_HPP_

#include <algorithm>
#include <ios>
#include <sstream>
#include <string>
#include <string_view>
#include <tuple>
#include <type_traits>

namespace rfl {

/// Used to define a field in the NamedTuple.
template <class T>
requires std::is_integral_v<T>
struct Oct {
  /// The underlying type.
  using Type = T;

  using ReflectionType = std::string;

  Oct() : value_(0) {}

  Oct(const Type& _value) : value_(_value) {}

  Oct(Oct<T>&& _other) noexcept = default;

  Oct(const Oct<T>& _other) = default;

  template <class U>
  Oct(const Oct<U>& _other) : value_(_other.get()) {}

  template <class U>
  Oct(Oct<U>&& _other) : value_(_other.get()) {}

  template <class U, typename std::enable_if<std::is_convertible_v<U, Type>,
                                             bool>::type = true>
  Oct(const U& _value) : value_(_value) {}

  template <class U, typename std::enable_if<std::is_convertible_v<U, Type>,
                                             bool>::type = true>
  Oct(U&& _value) noexcept : value_(std::forward<U>(_value)) {}

  template <class U, typename std::enable_if<std::is_convertible_v<U, Type>,
                                             bool>::type = true>
  Oct(const Oct<U>& _other) : value_(_other.value()) {}

  Oct(const std::string& _str) {
    std::istringstream(_str) >> std::oct >> value_;
  }

  ~Oct() = default;

  /// Returns the underlying object.
  const Type& get() const { return value_; }

  /// Returns the underlying object.
  Type& operator()() { return value_; }

  /// Returns the underlying object.
  const Type& operator()() const { return value_; }

  /// Assigns the underlying object.
  auto& operator=(const Type& _value) {
    value_ = _value;
    return *this;
  }

  /// Assigns the underlying object.
  template <class U, typename std::enable_if<std::is_convertible_v<U, Type>,
                                             bool>::type = true>
  auto& operator=(const U& _value) {
    value_ = _value;
    return *this;
  }

  /// Assigns the underlying object.
  Oct<T>& operator=(const Oct<T>& _other) = default;

  /// Assigns the underlying object.
  Oct<T>& operator=(Oct<T>&& _other) = default;

  /// Assigns the underlying object.
  template <class U>
  auto& operator=(const Oct<U>& _other) {
    value_ = _other.get();
    return *this;
  }

  /// Assigns the underlying object.
  template <class U>
  auto& operator=(const std::string& _str) {
    std::istringstream(_str) >> std::oct >> value_;
    return *this;
  }

  /// Assigns the underlying object.
  template <class U>
  auto& operator=(Oct<U>&& _other) {
    value_ = std::forward<T>(_other.value_);
    return *this;
  }

  /// Necessary for the automated parsing to work.
  std::string reflection() const {
    std::stringstream stream;
    stream << std::oct << value_;
    return stream.str();
  }

  /// Assigns the underlying object.
  void set(const Type& _value) { value_ = _value; }

  /// Returns the underlying value as a string, alias for .reflection().
  std::string str() const { return reflection(); }

  /// Returns the underlying object.
  Type& value() { return value_; }

  /// Returns the underlying object.
  const Type& value() const { return value_; }

  /// The underlying value.
  Type value_;
};

}  // namespace rfl

#endif  // RFL_FIELD_HPP_