【问题标题】:Is it possible to assign long long returne value to int64_t without losing the precision in a 64-bit Machine?是否可以将 long long 返回值分配给 int64_t 而不会丢失 64 位机器中的精度?
【发布时间】:2012-08-08 10:32:41
【问题描述】:

我已经实现了以下代码:

#include<stdio.h>
#include<string.h>
#include<ctype.h>
#include<cstdlib>
#include<sys/types.h>
main()
{
    int64_t i64value1 = 0;
    int64_t i64value2 = 0;
    long long llvalue = 0;
    const char *s = "10811535359";
    i64value1 = atoll(s);
    llvalue = atoll(s);
    i64value2 = llvalue;
    printf("s : [%s]\n",s);
    printf("i64value1 : [%d]\n",i64value1);
    printf("llvalue : [%lld]\n",llvalue);
    printf("i64value2 : [%d]\n",i64value2);
}

上述程序的输出是:

s : [10811535359]
i64value1 : [-2073366529]
llvalue : [10811535359]
i64value2 : [-2073366529]

使用的编译器是:

 gcc version 4.1.2 20080704 (Red Hat 4.1.2-48)

操作系统是 x86_64 GNU/Linux 2.6.18-194

因为 long long 是一个有符号的 64 位整数,并且在所有意图和目的上都与 int64_t 类型相同,逻辑上是 int64_tlong long 应该是等价的类型。并且有些地方提到使用 int64_t 而不是 long long。 但是当我查看 stdint.h 时,它告诉我为什么会看到上述行为:

# if __WORDSIZE == 64 
typedef long int  int64_t; 
# else 
__extension__ 
typedef long long int  int64_t; 
# endif 

在 64 位编译中,int64_tlong int,而不是 long long int

我的问题是,是否有一种解决方法/解决方案可以将 long long 返回值分配给 int64_t 而不会丢失 64 位机器中的精度?

提前致谢

【问题讨论】:

  • longlong long 在 x86_64 上是相同的。 int64_t 是一个正好有 64 位的类型,而 long long 至少long 一样大,long 至少 与 @ 一样大987654331@(顺便说一下,在这种情况下也是 64 位)。就目前而言,不用担心。
  • 如果 x86_64 你的意思是 Linux x86-64,这是真的。对于同一硬件上的 64 位 Windows(long 是 32 位),这绝对不是真的。

标签: c++ c


【解决方案1】:

损失不会发生在转换中,而是发生在打印中:

printf("i64value1 : [%d]\n",i64value1);

int64_t 参数的访问方式与int 一样。这是未定义的行为,但通常低 32 位是符​​号扩展的。

适当的编译器警告(例如 gcc -Wformat)应该会抱怨这一点。

【讨论】:

    【解决方案2】:

    Jilles 是对的。

    要么使用std::cout &lt;&lt;,我认为应该以正确的方式处理它,要么在打印时使用printf("i64value2 : [%lld]\n",i64value2); 应该解决它。

    【讨论】:

      【解决方案3】:

      x86-64 ABI 下 - long longlong 相同,即 64 位值。在这种情况下没有精度损失。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-02-08
        • 2017-09-25
        • 1970-01-01
        • 1970-01-01
        • 2011-10-26
        • 2011-05-08
        • 2013-12-31
        • 1970-01-01
        相关资源
        最近更新 更多