如何确定一个整数需要多少字节?

新手上路,请多包涵

我正在寻找最有效的方法来计算存储整数所需的最小字节数而不会丢失精度。

 e.g.

int: 10 = 1 byte
int: 257 = 2 bytes;
int: 18446744073709551615 (UINT64_MAX) = 8 bytes;

谢谢

PS这是一个哈希函数,将被调用数百万次

字节大小也不必是二的幂

最快的解决方案似乎是基于 tronics 的答案:

     int bytes;
    if (hash <= UINT32_MAX)
    {
        if (hash < 16777216U)
        {
            if (hash <= UINT16_MAX)
            {
                if (hash <= UINT8_MAX) bytes = 1;
                else bytes = 2;
            }
            else bytes = 3;
        }
        else bytes = 4;
    }
    else if (hash <= UINT64_MAX)
    {
        if (hash < 72057594000000000ULL)
        {
            if (hash < 281474976710656ULL)
            {
                if (hash < 1099511627776ULL) bytes = 5;
                else bytes = 6;
            }
            else bytes = 7;
        }
        else bytes = 8;
    }

与 Thomas Pornin 的答案相比,主要使用 56 位 val 的速度差异很小(但可测量)。我也没有使用 __builtin_clzl 测试解决方案,这可能是可比的。

原文由 user75832 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 834
2 个回答

如果您只对常见尺寸感兴趣,您只需要两个简单的 if s。考虑一下(假设您实际上有无符号值):

 if (val < 0x10000) {
    if (val < 0x100) // 8 bit
    else // 16 bit
} else {
    if (val < 0x100000000L) // 32 bit
    else // 64 bit
}

如果您需要测试其他尺寸,选择一个中间点然后进行嵌套测试将在任何情况下保持测试的数量非常低。但是,在这种情况下,使测试成为递归函数可能是更好的选择,以保持代码简单。一个体面的编译器将优化递归调用,以便生成的代码仍然一样快。

原文由 Tronic 发布,翻译遵循 CC BY-SA 2.5 许可协议

用这个:

 int n = 0;
while (x != 0) {
    x >>= 8;
    n ++;
}

这假设 x 包含您的(正)值。

请注意,零将被声明为可编码,因为根本没有字节。此外,大多数可变大小编码需要一些长度字段或终止符来知道编码在文件或流中停止的位置(通常,当您对整数进行编码并注意大小时,编码对象中有多个整数)。

原文由 Thomas Pornin 发布,翻译遵循 CC BY-SA 2.5 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题