Added more concepts
This commit is contained in:
parent
3b7d1dc159
commit
f625cb1503
@ -10,13 +10,19 @@ namespace gz::util {
|
|||||||
// CONVERT TO STRING CONCEPTS
|
// CONVERT TO STRING CONCEPTS
|
||||||
//
|
//
|
||||||
// ELEMENTARY TYPES
|
// ELEMENTARY TYPES
|
||||||
/// is (similar or convertible to) std::string
|
/// same as std::string
|
||||||
template<typename T>
|
template<typename T>
|
||||||
concept Stringy = std::same_as<T, std::string> || std::convertible_to<T, std::string_view>;
|
concept Stringy = std::same_as<T, std::string> || std::convertible_to<T, std::string_view>;
|
||||||
|
|
||||||
|
/// can construct std::string from T
|
||||||
|
template<typename T>
|
||||||
|
concept CanConstructString = !Stringy<T> && requires(const T& t) {
|
||||||
|
{ std::string(t) } -> std::same_as<std::string>;
|
||||||
|
};
|
||||||
|
|
||||||
/// has .to_string() const member
|
/// has .to_string() const member
|
||||||
template<typename T>
|
template<typename T>
|
||||||
concept HasToStringMember = !Stringy<T> && requires(const T& t) { { t.to_string() }-> Stringy; };
|
concept HasToStringMember = !Stringy<T> && requires(const T& t) { { t.toString() }-> Stringy; };
|
||||||
|
|
||||||
/// works with std::to_string(), except bool
|
/// works with std::to_string(), except bool
|
||||||
template<typename T>
|
template<typename T>
|
||||||
@ -84,11 +90,56 @@ namespace gz::util {
|
|||||||
// POINTER
|
// POINTER
|
||||||
/// Everything from string-convertibleNoPtr but "behind" a pointer
|
/// Everything from string-convertibleNoPtr but "behind" a pointer
|
||||||
template<typename T>
|
template<typename T>
|
||||||
concept PointerConvertibleToString = requires(const T t) { { *t } -> _ElementaryTypeOrContainerConvertibleToString; };
|
concept PointerConvertibleToString = !_ElementaryTypeOrContainerConvertibleToString<T> and
|
||||||
|
requires(const T t) { { *t } -> _ElementaryTypeOrContainerConvertibleToString; };
|
||||||
|
|
||||||
} // namespace gz::util
|
} // namespace gz::util
|
||||||
|
|
||||||
namespace gz {
|
|
||||||
|
//
|
||||||
|
// CONVERT TO STRING
|
||||||
|
//
|
||||||
|
template<typename T>
|
||||||
|
concept False = false;
|
||||||
|
/**
|
||||||
|
* @brief Declaration of fromString in global namespace, so that concepts can use it
|
||||||
|
* @details
|
||||||
|
* This declaration only exists so that ::fromString can be used in concepts.
|
||||||
|
*/
|
||||||
|
template<False T>
|
||||||
|
T fromString(const std::string& s);
|
||||||
|
/**
|
||||||
|
* @brief Declaration of toString in global namespace, so that concepts can use it
|
||||||
|
* This declaration only exists so that ::toString can be used in concepts.
|
||||||
|
*/
|
||||||
|
template<False T>
|
||||||
|
std::string toString(const T& s);
|
||||||
|
|
||||||
|
namespace gz::util {
|
||||||
|
template<typename T>
|
||||||
|
concept ConstructibleFromStringGlobal = requires(const std::string& s) {
|
||||||
|
{ ::fromString<T>(s) } -> std::same_as<T>;
|
||||||
|
};
|
||||||
|
template<typename T>
|
||||||
|
concept ConvertibleToStringGlobal = requires(const T& t) {
|
||||||
|
{ ::toString(t) } -> Stringy;
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief toString is implemented for these types
|
||||||
|
*/
|
||||||
|
template<typename T>
|
||||||
|
concept GetTypeFromStringImplemented =
|
||||||
|
std::same_as<T, int> or
|
||||||
|
std::same_as<T, long> or
|
||||||
|
std::same_as<T, long long> or
|
||||||
|
std::same_as<T, unsigned int> or
|
||||||
|
std::same_as<T, unsigned long> or
|
||||||
|
std::same_as<T, unsigned long long> or
|
||||||
|
std::same_as<T, float> or
|
||||||
|
std::same_as<T, double> or
|
||||||
|
std::same_as<T, long double> or
|
||||||
|
std::same_as<T, bool>;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -105,14 +105,14 @@ std::string getStringOr(const std::string& s, const std::string& fallback) noexc
|
|||||||
// CONVERT FROM STRING
|
// CONVERT FROM STRING
|
||||||
//
|
//
|
||||||
template<>
|
template<>
|
||||||
bool from_string<bool>(const std::string& s) {
|
bool fromString<bool>(const std::string& s) {
|
||||||
if (s == "true" or s == "True" or s == "1") {
|
if (s == "true" or s == "True" or s == "1") {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
else if (s == "false" or s == "False" or s == "0") {
|
else if (s == "false" or s == "False" or s == "0") {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
throw InvalidArgument("s is not a bool: '" + s + "'", "from_string<bool>");
|
throw InvalidArgument("s is not a bool: '" + s + "'", "fromString<bool>");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -78,20 +78,28 @@ namespace gz {
|
|||||||
* @{
|
* @{
|
||||||
*/
|
*/
|
||||||
/**
|
/**
|
||||||
* @brief Construct a string from a string like-type
|
* @brief Return the string
|
||||||
*/
|
*/
|
||||||
template<util::Stringy T>
|
template<util::Stringy T>
|
||||||
inline std::string to_string(const T& t) {
|
inline std::string toString(const T& t) {
|
||||||
return t;
|
return static_cast<std::string>(t);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Construct a string from a string like-type
|
||||||
|
*/
|
||||||
|
template<util::CanConstructString T>
|
||||||
|
inline std::string toString(const T& t) {
|
||||||
|
return std::string(t);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @overload
|
* @overload
|
||||||
* @brief Construct a string from a type having a to_string() const member function
|
* @brief Construct a string from a type having a toString() const member function
|
||||||
*/
|
*/
|
||||||
template<util::HasToStringMember T>
|
template<util::HasToStringMember T>
|
||||||
inline std::string to_string(const T& t) {
|
inline std::string toString(const T& t) {
|
||||||
return t.to_string();
|
return t.toString();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -100,7 +108,7 @@ namespace gz {
|
|||||||
* @returns std::to_string(t)
|
* @returns std::to_string(t)
|
||||||
*/
|
*/
|
||||||
template<util::WorksWithStdToString T>
|
template<util::WorksWithStdToString T>
|
||||||
inline std::string to_string(const T& t) {
|
inline std::string toString(const T& t) {
|
||||||
return std::to_string(t);
|
return std::to_string(t);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -110,7 +118,7 @@ namespace gz {
|
|||||||
* Unlike std::to_string(bool), which returns 0 or 1, this function returns "true" or "false"
|
* Unlike std::to_string(bool), which returns 0 or 1, this function returns "true" or "false"
|
||||||
* @returns "true" or "false"
|
* @returns "true" or "false"
|
||||||
*/
|
*/
|
||||||
inline std::string to_string(const bool& b) {
|
inline std::string toString(const bool& b) {
|
||||||
return b ? "true" : "false";
|
return b ? "true" : "false";
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -119,10 +127,10 @@ namespace gz {
|
|||||||
* @brief Construct a string from a forward range
|
* @brief Construct a string from a forward range
|
||||||
*/
|
*/
|
||||||
template<util::ContainerConvertibleToString T>
|
template<util::ContainerConvertibleToString T>
|
||||||
std::string to_string(const T& t) {
|
std::string toString(const T& t) {
|
||||||
std::string s = "[ ";
|
std::string s = "[ ";
|
||||||
for (auto it = t.begin(); it != t.end(); it++) {
|
for (auto it = t.begin(); it != t.end(); it++) {
|
||||||
s += to_string(*it) + ", ";
|
s += toString(*it) + ", ";
|
||||||
}
|
}
|
||||||
if (s.size() > 2) {
|
if (s.size() > 2) {
|
||||||
s.erase(s.size() - 2);
|
s.erase(s.size() - 2);
|
||||||
@ -136,8 +144,8 @@ namespace gz {
|
|||||||
* @brief Construct a string from a pair
|
* @brief Construct a string from a pair
|
||||||
*/
|
*/
|
||||||
template<util::PairConvertibleToString T>
|
template<util::PairConvertibleToString T>
|
||||||
inline std::string to_string(const T& t) {
|
inline std::string toString(const T& t) {
|
||||||
return "{ " + to_string(t.first) + ", " + to_string(t.second) + " }";
|
return "{ " + toString(t.first) + ", " + toString(t.second) + " }";
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -145,11 +153,11 @@ namespace gz {
|
|||||||
* @brief Construct a string from a forward range holding a pair, eg a map
|
* @brief Construct a string from a forward range holding a pair, eg a map
|
||||||
*/
|
*/
|
||||||
template<util::MapConvertibleToString T>
|
template<util::MapConvertibleToString T>
|
||||||
std::string to_string(const T& t) {
|
std::string toString(const T& t) {
|
||||||
std::string s = "{ ";
|
std::string s = "{ ";
|
||||||
for (const auto& [k, v] : t) {
|
for (const auto& [k, v] : t) {
|
||||||
s += to_string(k) + ": ";
|
s += toString(k) + ": ";
|
||||||
s += to_string(v) + ", ";
|
s += toString(v) + ", ";
|
||||||
}
|
}
|
||||||
if (s.size() > 2) {
|
if (s.size() > 2) {
|
||||||
s.erase(s.size() - 2);
|
s.erase(s.size() - 2);
|
||||||
@ -163,8 +171,8 @@ namespace gz {
|
|||||||
* @brief Construct a string from the element the pointer points at
|
* @brief Construct a string from the element the pointer points at
|
||||||
*/
|
*/
|
||||||
template<util::PointerConvertibleToString T>
|
template<util::PointerConvertibleToString T>
|
||||||
inline std::string to_string(const T& t) {
|
inline std::string toString(const T& t) {
|
||||||
return to_string(*t);
|
return toString(*t);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -172,10 +180,10 @@ namespace gz {
|
|||||||
* @brief Construct a string from a vector with x, y members
|
* @brief Construct a string from a vector with x, y members
|
||||||
*/
|
*/
|
||||||
template<util::Vector2ConvertibleToString T>
|
template<util::Vector2ConvertibleToString T>
|
||||||
inline std::string to_string(const T& t) {
|
inline std::string toString(const T& t) {
|
||||||
std::string s = "( ";
|
std::string s = "( ";
|
||||||
s += to_string(t.x) + ", ";
|
s += toString(t.x) + ", ";
|
||||||
s += to_string(t.z) + " )";
|
s += toString(t.z) + " )";
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -184,11 +192,11 @@ namespace gz {
|
|||||||
* @brief Construct a string from a vector with x, y members
|
* @brief Construct a string from a vector with x, y members
|
||||||
*/
|
*/
|
||||||
template<util::Vector3ConvertibleToString T>
|
template<util::Vector3ConvertibleToString T>
|
||||||
inline std::string to_string(const T& t) {
|
inline std::string toString(const T& t) {
|
||||||
std::string s = "( ";
|
std::string s = "( ";
|
||||||
s += to_string(t.x) + ", ";
|
s += toString(t.x) + ", ";
|
||||||
s += to_string(t.y) + ", ";
|
s += toString(t.y) + ", ";
|
||||||
s += to_string(t.z) + " )";
|
s += toString(t.z) + " )";
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -197,14 +205,23 @@ namespace gz {
|
|||||||
* @brief Construct a string from a vector with x, y, z, w members
|
* @brief Construct a string from a vector with x, y, z, w members
|
||||||
*/
|
*/
|
||||||
template<util::Vector4ConvertibleToString T>
|
template<util::Vector4ConvertibleToString T>
|
||||||
inline std::string to_string(const T& t) {
|
inline std::string toString(const T& t) {
|
||||||
std::string s = "( ";
|
std::string s = "( ";
|
||||||
s += to_string(t.x) + ", ";
|
s += toString(t.x) + ", ";
|
||||||
s += to_string(t.y) + ", ";
|
s += toString(t.y) + ", ";
|
||||||
s += to_string(t.z) + ", ";
|
s += toString(t.z) + ", ";
|
||||||
s += to_string(t.w) + " )";
|
s += toString(t.w) + " )";
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @overload
|
||||||
|
* @brief Construct a string from a type that has toString declared in global namespace
|
||||||
|
*/
|
||||||
|
template<util::ConvertibleToStringGlobal T>
|
||||||
|
inline std::string toString(const T& t) {
|
||||||
|
return ::toString(t);
|
||||||
|
}
|
||||||
/**
|
/**
|
||||||
* @}
|
* @}
|
||||||
*/
|
*/
|
||||||
@ -215,59 +232,50 @@ namespace gz {
|
|||||||
/**
|
/**
|
||||||
* @name Construct a type from a string
|
* @name Construct a type from a string
|
||||||
* @note
|
* @note
|
||||||
* The from_string()functions (except for the bool one) simply return std::stoXX. These can throw std::invalid_argument and std::out_of_range.
|
* The fromString()functions (except for the bool one) simply return std::stoXX. These can throw std::invalid_argument and std::out_of_range.
|
||||||
* See https://en.cppreference.com/w/cpp/string/basic_string/stol
|
* See https://en.cppreference.com/w/cpp/string/basic_string/stol
|
||||||
*/
|
*/
|
||||||
template<typename T>
|
|
||||||
concept GetTypeFromStringImplemented =
|
|
||||||
std::same_as<T, int> or
|
|
||||||
std::same_as<T, long> or
|
|
||||||
std::same_as<T, long long> or
|
|
||||||
std::same_as<T, unsigned int> or
|
|
||||||
std::same_as<T, unsigned long> or
|
|
||||||
std::same_as<T, unsigned long long> or
|
|
||||||
std::same_as<T, float> or
|
|
||||||
std::same_as<T, double> or
|
|
||||||
std::same_as<T, long double> or
|
|
||||||
std::same_as<T, bool>;
|
|
||||||
|
|
||||||
template<GetTypeFromStringImplemented T>
|
/**
|
||||||
T from_string(const std::string& s);
|
* @brief Declaration of fromString, but only for the types for which it is implemented
|
||||||
|
*/
|
||||||
|
template<util::GetTypeFromStringImplemented T>
|
||||||
|
T fromString(const std::string& s);
|
||||||
|
|
||||||
/// @returns std::stoi(s)
|
/// @returns std::stoi(s)
|
||||||
template<> inline int from_string<int>(const std::string& s) {
|
template<> inline int fromString<int>(const std::string& s) {
|
||||||
return std::stoi(s);
|
return std::stoi(s);
|
||||||
}
|
}
|
||||||
/// @returns std::stol(s)
|
/// @returns std::stol(s)
|
||||||
template<> inline long from_string<long>(const std::string& s) {
|
template<> inline long fromString<long>(const std::string& s) {
|
||||||
return std::stol(s);
|
return std::stol(s);
|
||||||
}
|
}
|
||||||
/// @returns std::stoll(s)
|
/// @returns std::stoll(s)
|
||||||
template<> inline long long from_string<long long>(const std::string& s) {
|
template<> inline long long fromString<long long>(const std::string& s) {
|
||||||
return std::stoll(s);
|
return std::stoll(s);
|
||||||
}
|
}
|
||||||
/// @returns std::stoul(s)
|
/// @returns std::stoul(s)
|
||||||
template<> inline unsigned int from_string<unsigned int>(const std::string& s) {
|
template<> inline unsigned int fromString<unsigned int>(const std::string& s) {
|
||||||
return std::stoul(s);
|
return std::stoul(s);
|
||||||
}
|
}
|
||||||
/// @returns std::stoul(s)
|
/// @returns std::stoul(s)
|
||||||
template<> inline unsigned long from_string<unsigned long>(const std::string& s) {
|
template<> inline unsigned long fromString<unsigned long>(const std::string& s) {
|
||||||
return std::stoul(s);
|
return std::stoul(s);
|
||||||
}
|
}
|
||||||
/// @returns std::stoull(s)
|
/// @returns std::stoull(s)
|
||||||
template<> inline unsigned long long from_string<unsigned long long>(const std::string& s) {
|
template<> inline unsigned long long fromString<unsigned long long>(const std::string& s) {
|
||||||
return std::stoull(s);
|
return std::stoull(s);
|
||||||
}
|
}
|
||||||
/// @returns std::stof(s)
|
/// @returns std::stof(s)
|
||||||
template<> inline float from_string<float>(const std::string& s) {
|
template<> inline float fromString<float>(const std::string& s) {
|
||||||
return std::stof(s);
|
return std::stof(s);
|
||||||
}
|
}
|
||||||
/// @returns std::stod(s)
|
/// @returns std::stod(s)
|
||||||
template<> inline double from_string<double>(const std::string& s) {
|
template<> inline double fromString<double>(const std::string& s) {
|
||||||
return std::stod(s);
|
return std::stod(s);
|
||||||
}
|
}
|
||||||
/// @returns std::stold(s)
|
/// @returns std::stold(s)
|
||||||
template<> inline long double from_string<long double>(const std::string& s) {
|
template<> inline long double fromString<long double>(const std::string& s) {
|
||||||
return std::stold(s);
|
return std::stold(s);
|
||||||
}
|
}
|
||||||
/**
|
/**
|
||||||
@ -277,34 +285,44 @@ namespace gz {
|
|||||||
* - returns false if s = "false" or "False" or "0"
|
* - returns false if s = "false" or "False" or "0"
|
||||||
* - throws InvalidArgument otherwise
|
* - throws InvalidArgument otherwise
|
||||||
*/
|
*/
|
||||||
template<> bool from_string<bool>(const std::string& s);
|
template<> bool fromString<bool>(const std::string& s);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @overload
|
||||||
|
* @brief Construct T from a string using a fromString that is declared in global namespace
|
||||||
|
*/
|
||||||
|
template<util::ConstructibleFromStringGlobal T>
|
||||||
|
inline T fromString(const std::string& s) {
|
||||||
|
return ::fromString<T>(s);
|
||||||
|
}
|
||||||
/**
|
/**
|
||||||
* @}
|
* @}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
//
|
//
|
||||||
// CONCEPTS
|
// CONCEPTS
|
||||||
//
|
//
|
||||||
/**
|
/**
|
||||||
* @brief Any type where to_string(t) const exists returns a string-like type
|
* @brief Any type where toString(t) const exists returns a string-like type
|
||||||
* @note The function only has to exist, it does not have to be noexcept!
|
* @note The function only has to exist, it does not have to be noexcept!
|
||||||
*/
|
*/
|
||||||
template<typename T>
|
template<typename T>
|
||||||
concept ConvertibleToString = requires(const T& t) { { to_string(t) } -> util::Stringy; };
|
concept ConvertibleToString = requires(const T& t) {
|
||||||
/* concept CovertibleToString = requires(const T& t) { { to_string(t) }; }; */
|
{ toString(t) } -> util::Stringy;
|
||||||
|
};
|
||||||
|
/* concept CovertibleToString = requires(const T& t) { { toString(t) }; }; */
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Any type where from_string(string) exists and returns T
|
* @brief Any type where fromString(string) exists and returns T
|
||||||
* @note The function only has to exist, it does not have to be noexcept!
|
* @note The function only has to exist, it does not have to be noexcept!
|
||||||
*/
|
*/
|
||||||
template<typename T>
|
template<typename T>
|
||||||
concept ConstructibleFromString = requires(const std::string& s) {
|
concept ConstructibleFromString = requires(const std::string& s) {
|
||||||
{ from_string<T>(s) } -> std::same_as<T>;
|
{ fromString<T>(s) } -> std::same_as<T>;
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Any type where to_string(t) and from_string(string) exist
|
* @brief Any type where toString(t) and fromString(string) exist
|
||||||
*/
|
*/
|
||||||
template<typename T>
|
template<typename T>
|
||||||
concept StringConvertible = ConvertibleToString<T> and ConstructibleFromString<T>;
|
concept StringConvertible = ConvertibleToString<T> and ConstructibleFromString<T>;
|
||||||
@ -328,29 +346,29 @@ namespace gz {
|
|||||||
* If you want to use your own data type with one of these,
|
* If you want to use your own data type with one of these,
|
||||||
* you can easily @ref sc_overloads "write your own string conversion" function for your custom datatype.
|
* you can easily @ref sc_overloads "write your own string conversion" function for your custom datatype.
|
||||||
*
|
*
|
||||||
* @section sc_to_string Convert to string
|
* @section sc_toString Convert to string
|
||||||
* You can use the to_string() function to turn certain types into strings.
|
* You can use the toString() function to turn certain types into strings.
|
||||||
* Concepts are used to determine the correct overload of the function.
|
* Concepts are used to determine the correct overload of the function.
|
||||||
*
|
*
|
||||||
* The concept ConvertibleToString is satisfied for types that can be converted to string
|
* The concept ConvertibleToString is satisfied for types that can be converted to string
|
||||||
* using to_string().
|
* using toString().
|
||||||
*
|
*
|
||||||
* @section sc_from_string Construct from string
|
* @section sc_fromString Construct from string
|
||||||
* You can use the from_string() function to create certain types from a string.
|
* You can use the fromString() function to create certain types from a string.
|
||||||
*
|
*
|
||||||
* The concept ConstructibleFromString is satisfied for types that can be constructed from a string with from_string().
|
* The concept ConstructibleFromString is satisfied for types that can be constructed from a string with fromString().
|
||||||
*
|
*
|
||||||
* When constructing something from a string, there is of course the problem that errors occur at runtime when
|
* When constructing something from a string, there is of course the problem that errors occur at runtime when
|
||||||
* the string is unsuitable for construction. In this case, the from_string functions from this library throw a InvalidArgument exception.
|
* the string is unsuitable for construction. In this case, the fromString functions from this library throw a InvalidArgument exception.
|
||||||
*
|
*
|
||||||
* @section sc_overloads Overloading the string conversion functions
|
* @section sc_overloads Overloading the string conversion functions
|
||||||
* @subsection sc_to_string_ov Overload for to_string
|
* @subsection sc_toString_ov Overload for toString
|
||||||
* If you want your custom type to be convertible to string, you have different options.
|
* If you want your custom type to be convertible to string, you have different options.
|
||||||
* You can either add an <code>to_string() const</code> member to your class or overload
|
* You can either add an <code>toString() const</code> member to your class or overload
|
||||||
* <code>std::string to_string(const T&)</code>.
|
* <code>std::string toString(const T&)</code>.
|
||||||
* Example for a class called <code>Custom</code>
|
* Example for a class called <code>Custom</code>
|
||||||
* @code
|
* @code
|
||||||
* std::string to_string(const Custom& c) {
|
* std::string toString(const Custom& c) {
|
||||||
* std::string s;
|
* std::string s;
|
||||||
* ...
|
* ...
|
||||||
* return s;
|
* return s;
|
||||||
@ -360,20 +378,20 @@ namespace gz {
|
|||||||
* so you have to at least declare it in a header file.
|
* so you have to at least declare it in a header file.
|
||||||
*
|
*
|
||||||
|
|
||||||
* @subsection sc_from_string_ov Overload for from_string
|
* @subsection sc_fromString_ov Overload for fromString
|
||||||
* Writing an overload for from_string needs a little bit more boiler plate.
|
* Writing an overload for fromString needs a little bit more boiler plate.
|
||||||
* Since from_string is a templated function, you need to declare it as such.
|
* Since fromString is a templated function, you need to declare it as such.
|
||||||
* The function declaration in this library uses a concept so that it is only
|
* The function declaration in this library uses a concept so that it is only
|
||||||
* declared for the types that are actully implemented.
|
* declared for the types that are actully implemented.
|
||||||
* Example for a class called <code>Custom</code>
|
* Example for a class called <code>Custom</code>
|
||||||
* @code
|
* @code
|
||||||
* // declare as template, but only for Custom
|
* // declare as template, but only for Custom
|
||||||
* template<std::same_as<Custom> T>
|
* template<std::same_as<Custom> T>
|
||||||
* Custom from_string(const std::string& s);
|
* Custom fromString(const std::string& s);
|
||||||
*
|
*
|
||||||
* // instantiation/definition, but only for Custom
|
* // instantiation/definition, but only for Custom
|
||||||
* template<>
|
* template<>
|
||||||
* Custom from_string<Custom>(const std::string& s) {
|
* Custom fromString<Custom>(const std::string& s) {
|
||||||
* ...
|
* ...
|
||||||
* return Custom(...);
|
* return Custom(...);
|
||||||
* };
|
* };
|
||||||
@ -384,15 +402,15 @@ namespace gz {
|
|||||||
* In other words:
|
* In other words:
|
||||||
* @code
|
* @code
|
||||||
* Custom c1;
|
* Custom c1;
|
||||||
* Custom c2 = from_string(to_string(c1));
|
* Custom c2 = fromString(toString(c1));
|
||||||
* assert(c1 == c2);
|
* assert(c1 == c2);
|
||||||
* @endcode
|
* @endcode
|
||||||
*
|
*
|
||||||
* SettingsManager expects the strings from to_string() to be a single line.
|
* SettingsManager expects the strings from toString() to be a single line.
|
||||||
* If it has multiple lines, it will not load it correctly when loading from a file.
|
* If it has multiple lines, it will not load it correctly when loading from a file.
|
||||||
*
|
*
|
||||||
* @todo Implement from_string for vectors that hold ConstructibleFromString types
|
* @todo Implement fromString for vectors that hold ConstructibleFromString types
|
||||||
* @todo Make from_string throw InvalidArgument, write docs
|
* @todo Make fromString throw InvalidArgument, write docs
|
||||||
* @todo Make macro for all types/concepts where someone would want to implement from_string and to_string explicitly, eg vectors
|
* @todo Make macro for all types/concepts where someone would want to implement fromString and toString explicitly, eg vectors
|
||||||
*/
|
*/
|
||||||
} // namespace gz
|
} // namespace gz
|
||||||
|
Loading…
Reference in New Issue
Block a user