Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can I obtain C++ type names in a constexpr way?

I would like to use the name of a type at compile time. For example, suppose I've written:

constexpr size_t my_strlen(const char* s) {         const char* cp = s;         while(*cp != '\0') { cp++; };         return cp - s; } 

and now I want to have:

template <typename T> constexpr auto type_name_length = my_strlen(typeid(T).name()); 

But alas, typeid(T).name() is just const char*, not constexpr... is there some other, constexpr way to get a type's name?

like image 975
einpoklum Avatar asked Mar 11 '16 13:03

einpoklum


People also ask

Does C have constexpr?

No, no such thing exists in C.

How do I know if a function is constexpr?

The easiest way to check whether a function (e.g., foo ) is constexpr is to assign its return value to a constexpr as below: constexpr auto i = foo(); if the returned value is not constexpr compilation will fail.

What is the use of constexpr in C++?

constexpr indicates that the value, or return value, is constant and, where possible, is computed at compile time. A constexpr integral value can be used wherever a const integer is required, such as in template arguments and array declarations.

Can std :: function be constexpr?

Constexpr constructors are permitted for classes that aren't literal types. For example, the default constructor of std::unique_ptr is constexpr, allowing constant initialization.


1 Answers

Well, you could, sort of, but probably not quite portable:

struct string_view {     char const* data;     std::size_t size; };  inline std::ostream& operator<<(std::ostream& o, string_view const& s) {     return o.write(s.data, s.size); }  template<class T> constexpr string_view get_name() {     char const* p = __PRETTY_FUNCTION__;     while (*p++ != '=');     for (; *p == ' '; ++p);     char const* p2 = p;     int count = 1;     for (;;++p2)     {         switch (*p2)         {         case '[':             ++count;             break;         case ']':             --count;             if (!count)                 return {p, std::size_t(p2 - p)};         }     }     return {}; } 

And you can define your desired type_name_length as:

template <typename T> constexpr auto type_name_length = get_name<T>().size; 

DEMO (works for clang & g++)

like image 142
Jamboree Avatar answered Sep 28 '22 06:09

Jamboree