首页 文章

是一个String数组,例如[串; 3]存储在堆栈或堆上?

提问于
浏览
3

Rust书指定:

使堆栈快速运行的另一个特性是堆栈上的所有数据必须占用已知的固定大小 .

它还说 String 存储在堆上,因为大小未知并且可能会发生变异 .

"composite"数据结构在哪里,如包含 String 的数组存储?阵列的大小是固定的,但阵列的组件大小可能会发生变化 .

let array: [String; 3] = ["A","B","C"];

存储此类“复合”数据类型的规则是什么?

2 回答

  • 12

    String 刚刚包裹 Vec<u8> . 所以这适用于所有 Vecs .

    Vec 在堆栈上有一个固定的大小:它的长度,容量和指向存储实际内容的堆的指针 .

    因此,在堆栈上有一个三个 Strings 的数组意味着这些字符串的"metadata"在堆栈上(长度,容量和指向数据的指针) .

    这些字符串的实际数据虽然存储在堆上,因为正确识别时它的长度可变 .

  • 3

    Both .


    术语点:在讨论类型的内存布局时,不应该谈论堆栈与堆,而是关于内联与离线1:

    • 内联意味着数据就在这里,

    • offline表示数据在指针后面(无论指向何处)都可用 .

    一个简单的例子,整数是内联存储的:

    //  i32
    +---+
    | 3 |
    +---+
    

    典型的 struct Point { x: i32, y: i32 } 也以内联方式存储:

    //  Point
    +---+---+
    | x | y |
    +---+---+
    

    String (通常表示为 struct String { data: *mut u8, len: usize, cap: usize } )内联和离线存储:

    //   String
    +-------+-------+-------+
    | data  |  len  |  cap  |
    +-------+-------+-------+
        |
         \
          +-------------+
          |Hello, World!|
          +-------------+
    

    内联部分是3个指针的存储空间,而离线部分是一个堆分配的记录,其中包含字符串 "Hello, World!" 的内容 .

    但是,内联并不总是意味着堆栈 . A Box<Point>

    //  Box<Point>
    +-------+
    | data  |
    +-------+
        |
         \
          +---+---+
          | x | y |
          +---+---+
    

    将其 Point (将其数据成员内联存储)存储在堆上!

    同样,离线并不总是意味着堆:

    fn main() {
        let i = 3;
        let r = &i;
    }
    

    这里, r 是一个引用(指针),它指向 i ,而 i 在堆栈中!

    1是的,我正在做这个,更好的条款将不胜感激 .


    那么,回到问题:

    它还说String存储在堆上,因为大小未知并且可能会发生变异 .

    这是一个近似值,如上所述, String 有一些内联数据(指针,长度和容量),有些数据在堆上(字符串内容) .

    “复合”数据结构在哪里,如包含String的数组存储?阵列的大小是固定的,但阵列的组件大小可能会发生变化 . let array:[String; 3] = [“A”,“B”,“C”];

    它存储在堆栈和堆中:

    //  [String; 3]
    +-------+-------+-------+-------+-------+-------+-------+-------+-------+
    | data  |  len  |  cap  | data  |  len  |  cap  | data  |  len  |  cap  |
    +-------+-------+-------+-------+-------+-------+-------+-------+-------+
        |                       |                       |    
         \                       \                       \
          +-+                     +-+                     +-+
          |A|                     |B|                     |C|
          +-+                     +-+                     +-+
    

    这是9个指针的内联数据(在堆栈中),以及堆上的3个单独分配 .

    存储此类“复合”数据类型的规则是什么?

    数据成员总是内联的,指针和引用可能指向脱机数据,这些数据可能在堆上,堆栈上等...

相关问题