isize
类型是带符号的整数类型,其位数与平台的指针类型相同。对象和数组大小的理论上限是最大isize
值。这样可以确保isize
可用于计算指向对象或数组的指针之间的差异,并且可以解决对象中的每个字节以及结束后的一个字节。
这显然将数组限制在32位系统上最多2G元素,但不清楚的是数组是否也被限制在最多2GB的内存。
在C或C ++中,您可以将指向第一个和最后一个元素的指针转换为char*
,并获得指向这两个元素的指针的差异;有效地将数组限制为2GB(以免它溢出intptr_t
)。
在Rust中,32位数组是否也限制为2GB?或者不是?
答案 0 :(得分:5)
Vec
的内部使用
with_capacity
和grow_capacity
的值限制为4GB
let size = capacity.checked_mul(mem::size_of::<T>())
.expect("capacity overflow");
如果指针溢出会发生混乱。
因此,Vec
- 分配的切片在Rust中也以这种方式加盖。鉴于这是因为分配API的基本限制,如果任何典型类型可以绕过这一点,我会感到惊讶。如果他们这样做,由于指针溢出,切片上的Index
将是不安全的。所以我希望不会。
但是,由于其他原因,可能仍然无法分配所有4GB。特别是,allocate
不允许您分配超过2GB(isize::MAX
个字节),因此Vec
仅限于此。
答案 1 :(得分:3)
Rust使用LLVM作为编译器后端。用于指针运算的LLVM指令(GetElementPtr
)采用有符号整数偏移,并且在溢出时具有未定义的行为,因此在针对32位平台时,无法索引到大于2GB的数组。
为避免未定义的行为,Rust将拒绝在单个分配中分配超过2 GB的内容。有关详细信息,请参阅Rust问题#18726。