如何识别变量的类型

How to Identify type of a variable

如何在 C++ 中正确识别变量类型。我试过这个来识别一种变量:

int a = 5;
std::cout << typeid(a).name() << std::endl;

而不是预期的输出 int,它给你:

i

我很困惑为什么会这样。它以某种方式只给你声明变量类型的第一个字母。 int 不是唯一的……还有这个:

 char a = 'A'
 std::cout << typeid(a).name() << std::endl;

Example Program

有没有简单的解决方法?任何帮助将不胜感激!

你的代码有两个问题,

首先 typeid(..).name() return 是一个实现定义的字符串,它可以是任何有效的字符串,它可以 return "" 对于每种类型,它甚至可以 return 每个程序执行的不同值(尽管我相信该值在执行期间不能改变)。 GCC(和 Clang?)return 不可读的名称,而 Visual C++ return 合理的名称(在本例中 int

其次如果a的类型是多态类型,typeid(a)会return对应a的动态类型的typeid而不是用于声明 a 的类型,而不是使用 typeid(decltype(a)).

遗憾的是,没有以人类可读或正确的 C++ 语法的方式获取类型名称的标准方法。 (如果你想要一种在 GCC 中工作的方式,请参阅 Unmangling the result of std::type_info::name

编辑 使用 Boost,您可以尝试 std::cout << boost::typeindex::type_id<decltype(a)>().pretty_name() << std::endl;,参见 Getting human readable and mangled type names

类型名称不应该是您期望的那样。请参阅 this answer for a way to get the actual type name. Note - it only works on gcc and, with some additional installation,关于 clang。

对于 Visual C++,您应该调用 UnDecorateSymbolName,但显然 ints are called int there

I Mean even if it is not understandable. For example if int is 32432423423403095590353095309530953, then its always gonna be same. So i can easily set a function to return what type the variable is...

你得到的结果已经满足了。也许这有助于解释您正在使用的 C++ 实现究竟如何获取您所看到的字符串。

g++ 实现 typeid(...).name() 使得它 returns 类型的 "ABI mangled" 名称。这是表示编译目标文件和库中使用的类型的一种特殊方式。如果将 C++ 代码编译成程序集,您会看到 "symbols" 标识生成的程序集代码与哪些函数或数据相关。例如,取函数:

int foo(double a, char b) {
    return a + b;
}

compile it to assembly,您会看到如下内容:

_Z3foodc:
.LFB0:
    .cfi_startproc
    movsbl  %dil, %edi
    cvtsi2sd    %edi, %xmm1
    addsd   %xmm1, %xmm0
    cvttsd2si   %xmm0, %eax
    ret
    .cfi_endproc

这里的第一行是'mangled'符号,用来标识函数int foo(double,char)。它包含表示函数名称的 "Z3foo",然后是表示第一个参数类型的 'd' 和表示第二个参数类型的 'c'。此符号用于标识二进制目标文件中的函数、库索引中的函数,以及其他想要 link 此函数的已编译对象等

您还可以 demangle symbols 使用 c++filt 工具。此工具会扫描您传递给它的任何文本,以查找符合 mangling 语法的内容,并将它们转换为更类似于这些类型在 C++ 源代码中的命名方式的内容。

g++ 实现了 Itanium C++ ABI 修改方案。它被大多数 unix 平台编译器使用。

所以,回到你的代码,猜猜类型 'int' 在这些符号中是如何表示的。

Itanium ABI specifies an additional function for demangling. Here's 使用它的示例。