假设我们的目标是一个特定的硬件架构,一个特定的操作系统(如果适用)和一个特定的“位数”(32对64等)。在这种情况下,可以安全地假设不同的编译器会对同一sizeof(T*)
使用相同的T
吗?标准是否适用于这种或那种方式?
即使标准不能保证,对于“用于正常使用和效率的大多数正常编译器来说,这是否适用?”我可以想象一个理论上的Hell ++会在允许的情况下使用不同的大小,但是人们实际使用的是编译器呢?
我也会对我认为与指针(std::size_t
,std::ptrdiff_t
,std::intptr_t
)密切相关的其他类型感兴趣。
作为“红利问题”,可以说其他内置类型(例如char
,int
,float
,long
)?但是,在编译器中遇到不同的大小并不会让我感到惊讶。
修改
需要考虑的另一件事:这会受到extern "C"
链接的影响吗?作为应用程序的一个例子,如果我有一个发布这个函数的库:
extern "C" void foo(void *);
理论上我可能无法正确调用函数,因为库的编译器使用了与编译器不同的sizeof(void*)
吗?
答案 0 :(得分:4)
不,指向不同数据类型的指针不需要具有相同的大小。指针可能没有“预期”大小的一个特殊情况是指向成员函数的指针。为了能够支持虚函数,成员函数指针通常使用某种结构,指针数组等来实现。例如,在我的架构上,void *
长度为8个字节,但(Foo::*)()
为16:
h2co3-macbook:~ h2co3$ cat quirk.cpp
#include <iostream>
#include <algorithm>
class Foo {
public:
void bar()
{
std::cout << "bar()" << std::endl;
}
};
int main()
{
std::cout << "sizeof void *: " << sizeof(void *) << std::endl;
std::cout << "sizeof (Foo::*)(): " << sizeof(&Foo::bar) << std::endl;
return 0;
}
h2co3-macbook:~ h2co3$ clang++ -Wall -o quirk quirk.cpp
h2co3-macbook:~ h2co3$ ./quirk
sizeof void *: 8
sizeof (Foo::*)(): 16
其他类型(int
,float
等)的大小也会因编译器,体系结构甚至某些编译器标志和设置而有很大差异。