在C中获取变量名的编程方式?

Alp*_*neo 31 c variables variable-names

我正在开发一个从变量转储数据的工具.我需要转储变量名称,以及值.

我的解决方案:将变量名称存储为字符串,并打印"变量名称",后跟其值.

是否有任何编程方式来了解变量名称?

Mat*_*ner 51

你可以尝试这样的事情:

#define DUMP(varname) fprintf(stderr, "%s = %x", #varname, varname);
Run Code Online (Sandbox Code Playgroud)

我曾经使用过这个标题,当我是C新手时,它可能包含一些有用的想法.例如,这将允许您打印C值并在一个中提供格式说明符(以及一些其他信息):

#define TRACE(fmt, var) \
        (error_at_line(0, 0, __FILE__, __LINE__, "%s : " fmt, #var, var))
Run Code Online (Sandbox Code Playgroud)

如果您正在使用C++,则可以使用传递的值的类型并适当地输出它.如果是这种情况,我可以提供一个更有利可图的例子来说明如何"漂亮地打印"变量值.


Gre*_*ill 11

在C中,变量名存在编译步骤(和链接步骤,如果变量是全局的),但在运行时不可用.您必须选择一个涉及指示变量名称的文字字符串的解决方案.


pax*_*blo 6

我实际上有一些代码可以做你想要的.它使用预处理器对变量名进行字符串化,以允许您将其打印出来.它转储变量名称和值(基于类型)和该变量的内存布局.以下程序显示了它是如何完成的:

#include <stdio.h>
#include <stdlib.h>

static void dumpMem (unsigned char *p, unsigned int s) {
    int i;
    unsigned char c[0x10];
    printf (">>      ");
    for (i = 0; i < 0x10; i++) printf (" +%x",i);
    printf (" +");
    for (i = 0; i < 0x10; i++) printf ("%x",i);
    printf ("\n");
    for (i = 0; i < ((s + 15) & 0xfff0); i++) {
        if ((i % 0x10) == 0) {
            if (i != 0) printf ("  %*.*s\n", 0x10, 0x10, c);
            printf (">> %04x ",i);
        }
        if (i < s) {
            printf (" %02x", p[i]);
            c[i & 0xf] = ((p[i] < 0x20) || (p[i] > 0x7e)) ? '.' : p[i];
        } else {
            printf ("   ");
            c[i & 0xf] = ' ';
        }
    }
    printf ("  %*.*s\n", 0x10, 0x10, c);
}
#define DUMPINT(x) do{printf("%s: %d\n",#x,x);dumpMem((char*)(&x),sizeof(int));}while(0)
#define DUMPSTR(x) do{printf("%s: %s\n",#x,x);dumpMem(x,strlen(x));}while(0)
#define DUMPMEM(x,s) do{printf("%s:\n",#x);dumpMem((char*)(&x),s);}while(0)

typedef struct {
    char c;
    int i;
    char c2[6];
} tStruct;

int main (void) {
    int i = 42;
    char *s = "Hello there, my name is Pax!";
    tStruct z;
    z.c = 'a'; z.i = 42; strcpy (z.c2,"Hello");

    DUMPINT (i);
    DUMPSTR (s);
    DUMPMEM (z,sizeof(z));

    return 0;
}
Run Code Online (Sandbox Code Playgroud)

这输出:

i: 42
>>       +0 +1 +2 +3 +4 +5 +6 +7 +8 +9 +a +b +c +d +e +f +0123456789abcdef
>> 0000  2a 00 00 00                                      *...
s: Hello there, my name is Pax!
>>       +0 +1 +2 +3 +4 +5 +6 +7 +8 +9 +a +b +c +d +e +f +0123456789abcdef
>> 0000  48 65 6c 6c 6f 20 74 68 65 72 65 2c 20 6d 79 20  Hello there, my
>> 0010  6e 61 6d 65 20 69 73 20 50 61 78 21              name is Pax!
z:
>>       +0 +1 +2 +3 +4 +5 +6 +7 +8 +9 +a +b +c +d +e +f +0123456789abcdef
>> 0000  61 b6 16 61 2a 00 00 00 48 65 6c 6c 6f 00 0d 61  a..a*...Hello..a
Run Code Online (Sandbox Code Playgroud)

而且,如果你想知道do {...} while (0)宏中的健全性,那就是将它放在代码中的任何地方,而不必担心你是否有足够的括号围绕它.


Sae*_*Mo7 5

更短的方式:

#define GET_VARIABLE_NAME(Variable) (#Variable)
Run Code Online (Sandbox Code Playgroud)

测试:

#include <string>
class MyClass {};


int main(int argc, char* argv[]) {
    int foo = 0;

    std::string var_name1 = GET_VARIABLE_NAME(foo);
     char* var_name2 = GET_VARIABLE_NAME(foo);
     char* var_name3 = GET_VARIABLE_NAME(MyClass);


    return 0;
}
Run Code Online (Sandbox Code Playgroud)