5/31/2023 0 Comments Strings theory book 1![]() So you must use a string through some indirection, and track its size dynamically. since the compiler needs to precompute the size of the stack, it can't allow for dynamically sized types to be stored in it. specifically, str is analogous to, which doesn't contain length information, and therefore its size is unknown. Strings in Rust are stored as arrays of bytes, guaranteed to be valid UTF-8 sequences. the stack can grow only to a certain point before you cause a stack overflow, and whenever you exit a lexical scope, all data that was bound in it is dropped.Īnd the heap is extra memory that your program can request from the OS, this allows you to manage it however you like, and not worry about it dropping when the scope exits. (actually in simple cases like that the compiler can optimize it away). but the a variable is computed at runtime, so the compiler reserver space for it in the stack and stores it there. The stack is were all your variables are, for instance: let a = 2 + 3 īoth 2 and 3 are constants, therefore they're kept in the data section. data in the data section is available during the entire program runtime and cannot be modified or appended. The data section is a part of your compiled program that contains all static data, such as string and integer literals. There are 3 places data can be put: the data section, the stack, and the heap. Similarly, I can take a &str of a String s with &s I can take a & of a Vec v with &v and it will reference a subsection of the vector. Str is with the added promise that "this slice of u8 must be a valid utf-8 string" Using this struct, we can dynamically shrink and grow the Vec to any size we want, but it requires an allocation, which is expensive. That's why we have Vec which is a struct that contains a pointer to the beginning of a slice, the size of the slice, and a capacity of how many more items can we append to the slice without reallocating. ![]() ![]() Importantly, you can not own a, you can only take a reference to it. References to unsized types are special, and contain both a pointer to the first element of the slice as well as the size of the slice. It means "a contiguous group of 0 or more u8s in a row next to each other in memory, it is unknown how many u8s there are" and is considered an "unsized type" because we don't know its size. This is called a deref coercion (coercions are special types of conversions that are so trivial they happen automatically). This is why the following works: fn foo(s: &str) The other slightly magical thing is that a &String can be coerced into a &str. Of course, the sized considerations don't apply to ints, because they always have a known size. So we use a reference to a str to work with it.Ī pointer to the start of the string in memoryĪ length This is different to C, which typically uses null-terminated strings.Ī string literal is a &str because it is just a pointer into the data section of the binary (which is where all the constants go). But a reference to any type (even an unsized type) is always a fixed size. Since str doesn't have a length known at compile time, you can't use it directly. To have a variable in a function, rust needs to create space for it in a stack frame, which requires that it has a size known at compile time. It stores its data on the heap using unsafe. It's just a normal struct with some fields. Str is essentially equivalent to - it's a contiguous region of bytes in memory of an unknown length.
0 Comments
Leave a Reply. |