将业务逻辑功能实现为宏是一个好主意吗?
我继承了一些遗留的c ++代码,我发现很多业务逻辑函数都是作为冗长的神秘宏实现的.
宏是否优于函数?使用宏的一般原理是什么?
什么样的逻辑最适合宏?
这是代码中的一个简单示例
#define INSERT_VALUES(IN,ID,EO) {\
double evaluationOutput = EO;\
int controls = 0;\
int input_controls = m_input_controls[IN];\
if(m_value_list[IN].ShouldProcess())\
{\
evaluationOutput = m_evaluationOutput[IN];\
controls = m_controls[IN];\
}\
VALUE_EXIST(evaluationOutput,controls,input_controls,IN,ID,Adj);\
m_evaluationOutput[IN] = controls > 0 ? evaluationOutput : 0.0;\
m_controls[IN] = controls;\
m_input_controls[IN] = input_controls;\
Run Code Online (Sandbox Code Playgroud)
}
在Effective C++中,Scott Meyers在第2项中指出:
身高
consts,enums和inlines以#defines
Meyers特别提到了编写宏而不是函数的做法,他说:
该
#define指令的另一个常见(错误)用法是使用它来实现看起来像函数但不会产生函数调用开销的宏.像这样的宏有很多缺点,只是考虑它们是痛苦的.
幸运的是,你不必忍受这种废话.通过使用内联函数的模板,您可以获得宏的所有效率以及常规函数的所有可预测行为和类型安全性.
[实际功能]遵守范围和访问规则.例如,谈论一个类是私有的内联函数是很有意义的.一般来说,宏没有办法做到这一点.
要具体回答你的问题:
#include和(可能)#ifdef/ #ifndef用于条件编译.正如迈耶斯在结束时所说:
目前还没有时间退出预处理器,但你绝对应该给它长时间的假期.
不,它们绝对不是功能的一般替代品.
宏能够处理代码本身不具备的功能,特别是在编译之前创建和修改令牌(代码).
作为交换,他们失去了所有类型的安全性,几乎所有可用于实际代码的语法糖.
当你必须做一些代码无法完成的事情,或者需要有条件地存在代码(超级调试诸如内存跟踪之类的东西)时,宏会派上用场.它们在提供更简洁或更易读的方式来处理特定事物方面也有一定的价值(一个常见的例子是#define SUCCESS(x) (x >= 0).但是,对于任何需要类型安全,异常捕获或由不常用的常用代码组成的内容在编译时变异,它们几乎永远不合适.大多数似乎可能是宏的代码可能在实际代码中更安全地表达,这对业务逻辑很重要.
您可以获得的最接近的经验法则是在编译期间是否需要发生某些事情或更改.如果是这样,请考虑使用宏,否则只需编写代码即可.请记住,模板算作代码,可以做很多你可能想要使用宏的东西,但可能会更安全一些.
| 归档时间: |
|
| 查看次数: |
5644 次 |
| 最近记录: |