【发布时间】:2011-02-25 22:16:15
【问题描述】:
我想知道在编译时对有符号类型(例如 -2 >> 1 是否为 -1)进行操作时检查右移是否是算术的最便携方法是什么。
我的想法是在编译时以某种方式检查这一点并能够检测到这一点,因此我可以编译不同版本的函数(取决于运算符 >> 是否真的是算术移位)。
通过阅读主题 Verifying that C / C++ signed right shift is arithmetic for a particular compiler?我想到了初始化一个标志
static const bool is_arithmetic_rs = (((signed int)-1)>>1) == ((signed int)-1));
并像这样在运行时对其进行测试:
if (is_arithmetic_rs) {
// some fast algorithm using arithmetic right shifts (using >> operator)
} else {
// the same algorithm without arithmetic right shifts (much slower)
}
但是,如果可能的话,我希望每次都避免这种分支。为简单起见,假设我想实现一个可移植的算术右移;如果我必须在每次调用函数时检查这一点,这将对性能产生巨大影响,所以如果可能的话,我想在编译时进行。
如果不存在进行此检查的可移植方式,是否有办法通过尽最大努力进行检查,例如使用 ifdefs 检查特定编译器/平台?
【问题讨论】:
-
您是否遇到过很多编译器都会出错?帮我们一个忙,记录他们的名字。
-
到目前为止我没有找到任何东西,但我没有找到任何东西。如果我找到任何我会在这里创建一个列表。
-
我认为这几乎不是问题,就像补码、符号/大小、填充位、EBCDIC 以及标准允许的许多其他荒谬的事情一样。
-
任何智能编译器都会在编译时确定表达式的结果,并优化测试和未使用的分支。别担心。
-
@HansPassant “弄错”是什么意思?这种转变的行为是实现定义的。
标签: c++ c portability bit-manipulation compile-time