displaying #define values in C

2019-03-06 10:09发布

I have a series of #defines from a library file header of this sort:

typedef int Lib_error;   

#define   LIB_ERROR_A      ((Lib_error) 0x0000) 
#define   LIB_ERROR_D      ((Lib_error) 0x0100)                   
#define   LIB_ERROR_F      ((Lib_error) 0x0200)                      
#define   LIB_ERROR_K      ((Lib_error) 0x0300)                
#define   LIB_ERROR_O      ((Lib_error) 0x0400)                
#define   LIB_ERROR_P      ((Lib_error) 0x0500)
#define   LIB_ERROR_R      ((Lib_error) 0x0600) 
#define   LIB_ERROR_X      ((Lib_error) 0x0700)             
#define   LIB_ERROR_Y      ((Lib_error) 0x0800) 
#define   LIB_ERROR_M      ((Lib_error) 0x0900) 
 /* and so on */

Is there any way apart I can print these values so if for example

uint MyError;
   /* printf("Error = %s",MyError); It should print the string LIB_ERROR_F instead of say 0x200 */

I could use lot's of if else for this but I was wondering if there was a cleverer way. Please note that I can't change the contents of library header file in anyway.

4条回答
淡お忘
2楼-- · 2019-03-06 10:21

There isn't a simple or automatic way to do it. You have to generate the list of numbers and names yourself, and provide a lookup function to map between number and name.

You might take a look at the ideas in the blog post 'Enums, Strings and Laziness'; it has some ideas that might help you. (That's closely related to the X-Macros at Dr Dobbs mentioned by Oli Charlesworth; the article there claims the technique goes back to the 60s, albeit that it must have been in a language other than C since C didn't exist back then.)

查看更多
我只想做你的唯一
3楼-- · 2019-03-06 10:22

Warning: The below code piece is just a sample. It can be improvised a lot which is for you to do. : )

Define a structure like below:

typedef struct ErrorStorage
{
  Lib_error err;
  char err_string[100];
}ErrNoStore;

ErrNoStore arrErr[25];

arrErr[0].err = LIB_ERROR_A;
strcpy(arrErr[0].err_string, "LIB_ERROR_A");
/... and so on .../

and later down in the code define a function like this and call it

void display_error(Lib_error errnum)
{
  int i = 0;

  for(i=0; i<25;i++)
  {
    if(errnum == arrErr[i].err)
    {
       printf("%s\n", arrErr[i].err_string);
    }
  }
}

}

查看更多
smile是对你的礼貌
4楼-- · 2019-03-06 10:26

Just generate a table by parsing those defines in some scripting language. Should be easy-ish to translate those defines to the declaration of a constant array of code, string structs which you can then iterate.
Assuming the library doesn't change often, you'll only need to do this once so you don't need to bother much with script corectness etc.

查看更多
家丑人穷心不美
5楼-- · 2019-03-06 10:29

People seem to have mixed feelings about them, but X-macros are one possible solution.

But if you can't change the header, then your only two options (AFAIK) are:

  • Doing it manually
  • Some form of code generation step in your build process. In your case, it should probably be possible by parsing the header file with sed (assuming you're working on Linux).
查看更多
登录 后发表回答