mirror of
https://github.com/aantron/better-enums.git
synced 2025-12-06 16:56:42 +08:00
Eliminated dynamic allocation.
When compile-time stringized constant name trimming is disabled (off by default), trimming happens "lazily" - the first time the user calls a function such as _to_string, the function allocates space for trimmed constant names and trims them there. With this change, space is reserved statically in a writeable char array, and trimming happens in that array instead.
This commit is contained in:
parent
98232ee4fb
commit
74b3a66284
40
enum.h
40
enum.h
@ -436,17 +436,20 @@ _namesMatchNocase(const char *stringizedName, const char *referenceName,
|
|||||||
}
|
}
|
||||||
|
|
||||||
inline void _trim_names(const char * const *raw_names,
|
inline void _trim_names(const char * const *raw_names,
|
||||||
const char **trimmed_names, std::size_t count)
|
const char **trimmed_names,
|
||||||
|
char *storage, std::size_t count)
|
||||||
{
|
{
|
||||||
|
std::size_t offset = 0;
|
||||||
|
|
||||||
for (std::size_t index = 0; index < count; ++index) {
|
for (std::size_t index = 0; index < count; ++index) {
|
||||||
std::size_t length =
|
trimmed_names[index] = storage + offset;
|
||||||
|
|
||||||
|
std::size_t trimmed_length =
|
||||||
std::strcspn(raw_names[index], BETTER_ENUMS__NAME_ENDERS);
|
std::strcspn(raw_names[index], BETTER_ENUMS__NAME_ENDERS);
|
||||||
char *trimmed = new char[length + 1];
|
storage[offset + trimmed_length] = '\0';
|
||||||
|
|
||||||
std::strncpy(trimmed, raw_names[index], length);
|
std::size_t raw_length = std::strlen(raw_names[index]);
|
||||||
trimmed[length] = '\0';
|
offset += raw_length + 1;
|
||||||
|
|
||||||
trimmed_names[index] = trimmed;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -554,6 +557,14 @@ constexpr const char *_final_ ## index = \
|
|||||||
BETTER_ENUMS__PP_MAP( \
|
BETTER_ENUMS__PP_MAP( \
|
||||||
BETTER_ENUMS__STRINGIZE_SINGLE, ignored, __VA_ARGS__))
|
BETTER_ENUMS__STRINGIZE_SINGLE, ignored, __VA_ARGS__))
|
||||||
|
|
||||||
|
#define BETTER_ENUMS__RESERVE_STORAGE_SINGLE(ignored, index, expression) \
|
||||||
|
#expression ","
|
||||||
|
|
||||||
|
#define BETTER_ENUMS__RESERVE_STORAGE(...) \
|
||||||
|
BETTER_ENUMS__ID( \
|
||||||
|
BETTER_ENUMS__PP_MAP( \
|
||||||
|
BETTER_ENUMS__RESERVE_STORAGE_SINGLE, ignored, __VA_ARGS__))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// TODO Convert integral to underlying only at the last possible moment, if the
|
// TODO Convert integral to underlying only at the last possible moment, if the
|
||||||
@ -902,6 +913,13 @@ BETTER_ENUMS__CONSTEXPR inline bool operator !=(const Enum &a, const Enum &b) \
|
|||||||
return value; \
|
return value; \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
|
inline char* name_storage() \
|
||||||
|
{ \
|
||||||
|
static char storage[] = \
|
||||||
|
BETTER_ENUMS__ID(BETTER_ENUMS__RESERVE_STORAGE(__VA_ARGS__)); \
|
||||||
|
return storage; \
|
||||||
|
} \
|
||||||
|
\
|
||||||
inline const char** name_array() \
|
inline const char** name_array() \
|
||||||
{ \
|
{ \
|
||||||
static const char *value[Enum::_size]; \
|
static const char *value[Enum::_size]; \
|
||||||
@ -924,6 +942,13 @@ BETTER_ENUMS__CONSTEXPR inline bool operator !=(const Enum &a, const Enum &b) \
|
|||||||
return the_raw_names; \
|
return the_raw_names; \
|
||||||
} \
|
} \
|
||||||
\
|
\
|
||||||
|
inline char* name_storage() \
|
||||||
|
{ \
|
||||||
|
static char storage[] = \
|
||||||
|
BETTER_ENUMS__ID(BETTER_ENUMS__RESERVE_STORAGE(__VA_ARGS__)); \
|
||||||
|
return storage; \
|
||||||
|
} \
|
||||||
|
\
|
||||||
inline const char** name_array() \
|
inline const char** name_array() \
|
||||||
{ \
|
{ \
|
||||||
static const char *value[Enum::_size]; \
|
static const char *value[Enum::_size]; \
|
||||||
@ -976,6 +1001,7 @@ BETTER_ENUMS__CONSTEXPR inline bool operator !=(const Enum &a, const Enum &b) \
|
|||||||
\
|
\
|
||||||
::better_enums::_trim_names(BETTER_ENUMS__NS(Enum)::raw_names(), \
|
::better_enums::_trim_names(BETTER_ENUMS__NS(Enum)::raw_names(), \
|
||||||
BETTER_ENUMS__NS(Enum)::name_array(), \
|
BETTER_ENUMS__NS(Enum)::name_array(), \
|
||||||
|
BETTER_ENUMS__NS(Enum)::name_storage(), \
|
||||||
_size); \
|
_size); \
|
||||||
\
|
\
|
||||||
BETTER_ENUMS__NS(Enum)::initialized() = true; \
|
BETTER_ENUMS__NS(Enum)::initialized() = true; \
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user