宏观问题

时间:2009-04-02 13:27:23

标签: c macros

在软件项目(一些旧的C编译器)上,我们有很多变量必须保存正常和反转。

有人知道如何制作这样的宏吗?

SET(SomeVariable, 137);

将执行

SomeVariable = 137;
SomeVariable_inverse = ~137;

编辑:

最佳解决方案似乎是:

#define SET(var,value) do { var = (value); var##_inverse = ~(value); } while(0)

感谢您的回答

6 个答案:

答案 0 :(得分:11)

答案 1 :(得分:5)

我未提及的一个危险是在大多数解决方案中,'value'宏参数被评估两次。如果有人尝试这样的事情,这可能会导致问题:

int x = 10;
SET(myVariable, x++);

在此调用之后,myVariable将为10,myVariable_inverse将为~11。哎呀。对JaredPar解决方案的一个小改动解决了这个问题:

#define SET(var,value) do { var = (value); var##_inverse = ~(var); } while(0)

答案 2 :(得分:4)

为什么在可以如此轻松地计算时存储逆?这对我来说似乎是一个坏主意。

答案 3 :(得分:4)

您可以在一个语句中执行此操作,从而避免使用do {} while (0)

#define SetInverse(token, value) (token##_inverse = ~(token = (value)))

此外,这只会评估(value)一次,这总是很好。

答案 4 :(得分:1)

#define SetInverse(token, value) { token = value; token##_inverse = ~value; }

Jinx,Jared - 喜欢你的时间(0)

答案 5 :(得分:0)

只是提供另一种方法:

将每个变量存储为如下结构:

typedef struct
{
    u32 u32Normal;
    u32 u32Inverted;
} SafeU32TYPE

然后有一个函数,它带有一个指向其中一个的函数,以及要设置的值,并用反函数存储该值:

void Set(SafeU32TYPE *pSafeU32, u32Data)
{
    if(pSafeU32 != NULL)
    {
        pSafeU32->u32Normal = u32Data;
        pSageU32->u32Inverted = ~u32Data;
    } /* if */
} /* Set() */

优势:如果您需要set功能来执行更强大的功能,例如边界检查,或以更复杂的方式存储,那么它可以轻松扩展。

缺点:对于所使用的每种类型,您都需要不同的功能,如果处理器资源存在问题,则效率低于使用宏。