作者FRAXIS (喔喔)
看板C_and_CPP
标题[心得] X-Macros
时间Mon Jun 29 22:36:41 2009
以前在网路上乱逛的时候看到的技巧,跟大家分享。
假设有一个enum,其中包含三个item:first, second, third。
enum order { first, second, third };
然後我希望可以建立一个字串阵列,可以跟这个enum一对一对应
const char *array[] = { "first", "second", "third" };
但是这边有一个麻烦是,如果哪一天改了order,却忘记改array
的内容,程式就会出错。同时间维护两边的一致性很麻烦,所以才
产生了X-Macros的技巧。
当然,解决一致性的问题不只这种方法,这方法多少也降低了程式
的可读性,还会增加除错的困难。
下面是一个很简单的范例
先写一个data.def的档案,内容如下
X(0, first)
X(1, second)
X(2, third)
然後在宣告enum的地方改成
#define X(a,b) b=a,
enum order {
#include "data.def"
};
#undef X
这边会自动把order展开成
enum order {
first=0,
second=1,
third=2,
};
然後在array宣告的地方改成
#define X(a, b) [a]=#a,
const char *array[] = {
#include "data.def"
};
#undef X
这边会自动把array展开成
const char *array[] = {
[first]="first",
[second]="second",
[third]="third",
};
所以array[first] = "first", array[second] = "second",
array[third] = "third"
这边有用到C99的语法,用ANSI C的话要稍微修改一下。
如果此时要新增一项fourth,只要改变data.def即可。
以这个技巧延伸,可以把X的定义修改,让它除了可以产生资料的
宣告之外,还可以产生程式码,只是用巨集做越多事情,程式会越
难维护就是了。
如果要看更进阶的用法,请参考下列网站
http://en.wikipedia.org/wiki/C_preprocessor#X-Macros
http://www.ddj.com/cpp/184401387
http://op.closedformodification.com/2006/06/18/x-macros/
http://liw.iki.fi/liw/texts/cpp-trick.html
--
※ 发信站: 批踢踢实业坊(ptt.cc)
◆ From: 140.119.162.51
1F:推 bobhsiao:推分享啊~你挖出好多有趣的东西 06/29 23:00
2F:推 james732:很奇妙,推!! 06/30 04:42