繁体   English   中英

查找包含 vec 的类型的分配大小

[英]Find allocated size of type which holds a vec

我可以通过调用https://doc.rust-lang.org/std/mem/fn.size_of_val.html来查找一个值有多大。 这对于vec不起作用(在我的情况下),因为在不取消引用时大小始终为 32,无论有多少元素。

我在下面添加了一些代码,我希望Incoming struct的字节数至少与变量vec的字节一样大,因为Incoming struct包含vec

在调用size_of_val时直接取消vec会给我正确的vec大小,但我无法对持有vec的类型做类似的事情。

use std::mem::size_of_val;

#[derive(Debug)]
enum Incoming {
    Bytes(Vec<u8>),
    SomethingElse(String),
    Fixed(i64)
}

fn main() {
    let vec = vec![1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3, 1, 2, 3];

    // 39
    println!("Vec's real size: {} bytes", size_of_val(&*vec));

    let incoming = Incoming::Bytes(vec);
    let size_of = size_of_val(&incoming);

    // 32
    println!("But incoming tells me it's size is {} bytes", size_of);
}

是否可以为持有vec的类型获得分配的 memory ?

用例: Incoming代表我的 Rust 服务器将处理的所有不同请求。 我想调试记录每个请求。 一些请求可以包含带有许多元素的Vec<u8> 在这种情况下,我不想记录该请求,因为它实际上需要几分钟时间。

size_ofsize_of_val都指数据结构的“顶级”足迹。 例如,如果您有一个链表,其中每个节点是 48 字节,并且链表包含一百万个元素,那么size_of将只返回 48,而不是 4800 万。

在 Rust 中没有自动计算数据结构的总分配大小的方法,尤其是因为包括摊销分配开销成本或计算共享、循环或自引用数据结构的大小可能很重要。

您可能只想为所需的数据结构系列做自己的特征。

trait EstimableSize {
    fn estimate_size(&self) -> usize;
}

请求size_of_val(&*vec)时,首先deref ( * ) vec ,然后获得实际包含数据的切片,然后size_of_val()应用于该切片。

如果您忘记了* ,那么您将获得Vec结构本身的大小,与堆分配数据的实际数量无关。

当涉及到incoming时,它与没有 deref 的vec非常相似。

如果您想要堆分配的数据量(就我们而言,而不是内部开销),您必须深入研究incoming的 .

    match incoming {
        Incoming::Bytes(ref b) => {
            let sz = size_of_val(&**b); // one deref for b, another for the Vec
            println!("bytes stored inside incoming: {}", sz);
        }
        Incoming::SomethingElse(ref t) => {
            let sz = size_of_val(&**t); // one deref for t, another for the String
            println!("text stored inside incoming: {}", sz);
        }
        Incoming::Fixed(ref f) => {
            let sz = size_of_val(&*f); // one deref for f
            println!("integer stored inside incoming: {}", sz); // no surprise here
        }
    }

我无法改进@NovaDenizen 的回答:不,因为size_of_val()很浅。 但是,我想您可能想知道数据结构的分配大小。

这取决于几件事,包括:

  • memory分配器的选择,
  • 堆的碎片,
  • 该结构在什么上下文中使用(例如,它是在堆栈中还是在堆中?),
  • 编译器是否优化了它。

但是,使用 Rust 的默认 memory 分配器,如果没有碎片,并且分配一个 Box(并且不计算 Box),则可以按如下方式计算总大小:

  • 对于包含传入本身的块,大小为 32 个字节( size_of_val() )加上 8 个字节(1 个字 header 由 memory 分配器添加)加上 8 个字节(填充为 16 个字节的倍数),即 48 个字节。
  • 对于包含 Vec 元素的块,大小为 39 个字节(每个元素 1 个字节)加上 8 个字节(1 个字头)加上 1 个字节(填充到 16 个字节的倍数),即 48 个字节。

所以答案大概是 96 个字节。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM