&[T] are commonly created from stack allocated arrays, and &str are even more commonly created from read only string literals... so I don't think it's correct so say that those "usually" point to things on the heap. (But of course the definition of "usually" could vary, it wouldn't shock me to find out they did 60% of the time).
Or did you mean &T usually points to things on the heap, in which case I should just say it very very commonly points to stack allocated things as well.
&[T] are commonly created from stack allocated arrays,
Really? I would say that in my typical Rust code &[T] is created from a heap-allocated array >90% of the time. Most functions that do not require ownership of an argument will use &[T] and not &Vec<T> (or perhaps S: AsRef<[T]>), since &[T] works for stack and heap memory and &Vec<T> is automatically converted to &[T] through Deref coercion.
E.g.:
fn main() {
let v = vec![1, 2, 3, 4, 5];
blah(&v);
}
fn blah<T>(s: &[T]) {
println!("{}", s.len());
}
When you pass a `Vec<T>` directly to a non-mutating function or method not implemented on `Vec<T>` itself you pass it as a `&[T]`. But more often I pass it as part of a struct so it remains as (indirectly) `&Vec<T>`. However pretty much whenever you use a stack allocated array you use it as a &[T], part of a struct or not. I'm sure I use a heap allocated &[T] more often, but I doubt it reaches 90%.
For &str you have to remember that every string literal in your program is one. When you do `some_String.starts_with("/mnt")`, `println!("hi there {}", name)`, etc you are using a new &str. I suspect most programs use more static strings than dynamic Strings (particularly since Rust isn't heavily used in GUIs yet).
Or did you mean &T usually points to things on the heap, in which case I should just say it very very commonly points to stack allocated things as well.