通用架构的最快整数类型

时间:2010-09-12 07:54:41

标签: c performance architecture integer stdint

stdint.h标头缺少int_fastest_tuint_fastest_t{,u}int_fastX_t类型对应。对于整数类型的宽度无关紧要的情况,如何选择允许处理最大位数且性能损失最小的整数类型?例如,如果使用朴素方法在缓冲区中搜索第一个设置位,则可以考虑这样的循环:

// return the bit offset of the first 1 bit
size_t find_first_bit_set(void const *const buf)
{
    uint_fastest_t const *p = buf; // use the fastest type for comparison to zero
    for (; *p == 0; ++p); // inc p while no bits are set
    // return offset of first bit set
    return (p - buf) * sizeof(*p) * CHAR_BIT + ffsX(*p) - 1;
}

当然,使用char会导致比int更多的操作。但是long long可能导致比在32位系统上使用int的开销更昂贵的操作,等等。

我目前的假设是针对主流架构,使用long是最安全的选择:32位系统为32位,64位系统为64位。

9 个答案:

答案 0 :(得分:8)

int_fast8_t始终是正确实现中最快的整数类型。永远不会有小于8位的整数类型(因为需要CHAR_BIT>=8),并且由于int_fast8_t是具有至少8位的最快整数类型,因此它是最快的整数类型,周期。

答案 1 :(得分:3)

我不确定我是否真的理解这个问题,但为什么你不只是使用 int ?引用我的(错误的自由草案,即C ++)标准,“简单的内容具有执行环境体系结构所建议的自然大小。”

但我认为如果你想为某个操作获得最佳整数类型,它将根据它的操作而不同。试图找到大数据缓冲区中的第一个位,或者在整数序列中找到一个数字,或者移动它们,可能会有完全不同的最佳类型。

编辑:

无论价值多少,我都做了一个小基准。在我的特定系统(带有Linux的英特尔i7 920,gcc -O3)上,结果证明,在这个特定的例子中,长整数(64位)比普通整数(32位)快得多。我猜对了。

答案 2 :(得分:3)

理论上,int是最好的选择。它应映射到CPU的本机寄存器大小,因此在您询问的意义上是“最佳”。

但是,你可能仍然发现int-64或int-128在某些CPU上比int-32更快,因为虽然它们大于寄存器大小,但它们会减少循环的迭代次数,因此可以通过最小化循环开销和/或利用DMA更快地加载/存储数据来提高效率。

(例如,在ARM-2处理器上,加载一个32位寄存器需要4个存储周期,但只需5个周期就可以顺序加载2个周期,7个周期可以顺序加载4个。上面建议的例程将进行优化使用尽可能多的寄存器(通常为8到10),因此每次循环迭代使用多个寄存器可以使运行速度提高3到4倍。

唯一可以确定的方法是编写几个例程,然后在特定的目标机器上对它们进行分析,以找出哪个例程能够产生最佳性能。

答案 3 :(得分:2)

如果你想确定你有最快的实现,为什么不在你期望运行的系统上对每一个进行基准测试,而不是试图猜测?

答案 4 :(得分:1)

我猜测类型size_t(对于无符号类型)和ptrdiff_t(对于有符号类型)通常对应于任何给定平台上非常有效的整数类型。

但是没有什么可以证明这一点,而不是检查生产的汇编程序并做基准测试。

修改,包括不同的评论,此处和其他回复:

size_tptrdiff_t是唯一在C99中具有规范性的typedef,可以合理地假设它们与架构相关。

标准整数类型有5种不同的可能等级(charshortintlonglong long)。所有的力都朝向具有宽度8,16,32,64的类型并且在不久的将来128.结果int将被卡在32位上。它的定义与平台上的效率无关,只是受到宽度要求的限制。

答案 5 :(得分:1)

答案是int本身。至少在C ++中,标准的3.9.1 / 2表示:

  

普通int具有自然尺寸   建筑的建议   执行环境

我希望C也是如此,尽管我没有任何标准文件。

答案 6 :(得分:0)

如果您正在使用gcc进行编译,我建议使用__builtin_ffs()来查找第一个位集:

  

内置函数:int __builtin_ffs(unsigned int x)   返回一个加上x的最低有效1位的索引,或者如果x为零,则返回零。

这将编译成(通常是单个)本机汇编指令。

答案 7 :(得分:0)

由于问题不完整,因此无法回答这个问题。作为类比,请考虑以下问题:

  

什么是最快的车辆

A Bugatti Veyron?当然很快,但从伦敦到纽约没有好处。

问题中缺少的是整数将用于的上下文。在上面的原始示例中,我怀疑如果数组很大且稀疏,您会看到8位,32位或64位值之间存在很大差异你将在cpu限制之前达到内存带宽限制。

重点是,架构没有定义各种整数类型的大小,编译器设计者就是这样做的。设计师将仔细权衡针对给定架构的每种类型的各种尺寸的优缺点,并选择最合适的。

我猜选择64位系统上的32位int是因为大多数操作int用于32位就足够了。由于内存带宽是一个限制因素,节省内存使用可能是最重要的因素。

答案 8 :(得分:0)

对于所有现有的主流架构long是目前环路吞吐量最快的类型。