【问题标题】:If on my machine sizeof(long) == sizeof(long long), why aren't they the same type?如果在我的机器上 sizeof(long) == sizeof(long long),为什么它们不是同一类型?
【发布时间】:2016-12-23 16:12:15
【问题描述】:

如果我跑:

#include <type_traits>
#include <iostream>

int main()
{
    std::cout << "sizeof(long) = " << sizeof(long) << "\n";
    std::cout << "sizeof(long long) = " << sizeof(long long) << "\n";
    std::cout << "std::is_same<long, long long>::value = " 
        << std::boolalpha << std::is_same<long, long long>::value 
        << "\n";
    return 0;
}

在我的机器(和 Coliru)上,我get

sizeof(long) = 8
sizeof(long long) = 8
std::is_same<long, long long>::value = false

不仅仅是std::is_same&lt;&gt;;期望 int64_t 实例化的翻译单元失败,因为我只在另一个翻译单元中为 intlong long int 编译,尽管这一切都发生在同一台机器上。

为什么这些类型不一样?我的意思是,表现出与 typedef 相同类型的行为一样?

【问题讨论】:

  • 我认为这个问题没有任何问题。它包含一个可编译的示例,以及预期和记录的输出。为什么它被否决了?
  • 恕我直言,显而易见的程度不应成为否决的因素。广义相对论的问题对我的老教授来说是显而易见的。
  • char 是有符号或无符号的,但 char 既不是 signed char 也不是 unsigned charwchar_t 必须是一个独特的类型,而不是另一个整数类型
  • @einpoklum 正如 Bathsheba 所说,这是一个语言规则,所以你遵循它很简单。你处理谷物而不是反对它。
  • @einpoklum 因为它们是内置类型。没有内置类型是另一种类型的别名。实现可能使用相同的东西,但就代码而言,它们是不同的。该标准在如何实际实现内置类型方面提供了很大的余地。

标签: c++ types 64-bit int64 long-long


【解决方案1】:

这是语言规则,对可移植性至关重要。

intlonglong long 都被语言视为不同的类型,即使它们具有相同的字节数和补码方案。

这是故意的。这意味着您可以编写可以在类型大小不同的不同平台上编译的代码。

如果说两个重载会很烦人

void foo(int f)

void foo(long f)

在一个平台上被视为相同的函数,而在另一个平台上被视为不同的重载。

【讨论】:

  • 它可能会编译,但它也可能会做一些超出我预期的事情......无论如何,为不同大小的机器编写代码是很棘手的。但是,好吧,我能说什么,我猜这就是答案。
  • @einpoklum 如果它们是相同的类型,那么编写两个重载将违反单一定义规则(因为实际上这将是一个以两种不同方式编写的重载)。这会在某些平台上导致编译错误,而在其他平台上则不会。这在任何方面都是不可接受的。
  • @RichardHodges:另一方面,就目前的情况而言,int8_tint16_tint32_tint64_t 无法涵盖所有​​整数类型。跨度>
  • @einpoklum:我不确定这是否相关。固定宽度有符号类型都需要 2 的补码。我所说的内置类型可以是 1 的补码、2 的补码或有符号幅度。 C++ 旨在针对奇异架构。
  • @Bathsheba:这实际上是一个有趣的观点,它更清楚地说明了为什么大小和符号不足以确定整数类型。
【解决方案2】:

同样,这个程序:

#include <type_traits>
#include <iostream>

int main()
{
    using ::std::cout;
    using ::std::is_same;
    using ::std::boolalpha;

    cout << "sizeof(long) = " << sizeof(long) << "\n";
    cout << "sizeof(long long) = " << sizeof(long long) << "\n";
    cout << "sizeof(double) = " << sizeof(double) << "\n";
    cout << "::std::is_same<long, long long>::value = " 
        << boolalpha << is_same<long, long long>::value 
        << "\n";
    std::cout << "::std::is_same<long, double>::value = " 
        << boolalpha << is_same<long, double>::value 
        << "\n";
    return 0;
}

输出这个:

sizeof(long) = 8
sizeof(long long) = 8
sizeof(double) = 8
::std::is_same<long, long long>::value = false
::std::is_same<long, double>::value = false

如您所见,doublelong 的长度似乎相同,为什么它们不只是相同类型的 typedef?

【讨论】:

  • 这些类型的语义不同。 8 字节 long 的行为与 8 字节 long long 完全相同(我的意思是整数)。
  • @einpoklum,是的,这是不同的。不过,我会争辩说,由于重载差异等原因,它们没有完全相同的语义。
猜你喜欢
  • 2013-12-05
  • 2013-09-24
  • 2021-12-04
  • 1970-01-01
  • 2011-01-20
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多