It is the explicit return type on the inner closure, not on the spawn function. The closure will return Child, and spawn will return JoinHandle<Child>, correspondingly.
Explicit type might be necessary, if Rust is unable to infer it. Not sure if this is the case here. And the type parameter of JoinHandle is the thing you get on joining the thread.
In other languages it can be called anonymous function, or lambda, or closure. Specifically || part means that this closure does not have parameters. If it had, then it would be | param1, param2 | -> {...}.
Usually closure return type is not needed and will be iferred by compiler, for example || -> 3_u32 is the same as || -> u32 { 3_u32 }
On the other hand, || -> 3_u32 is not valid, as then 3_u32 is counted as the return type, and the closure has no body. The || declares the closure, and -> declares the return type. If no return type is specified, then you don't need ->. Note that this roughly matches function syntax, where you can write fn x() { ... } to return (), or fn x() -> u32 { ... } to return u32.
What do you mean by "does type do"? Types, AFAIK, can't do anything. Values can.
Or do you mean if the presence or absence of this return type changes anything? I'm not sure, but it may turn program failing to compile (due to type inference error) into one which compiles.
Types in Rust always exist, but they may be either explicitly specified by the programmer, or inferred by the compiler.
Functions always have explicit types:
fn double(x: i32) -> i32 { x * 2 }
Closures may have explicit types:
let double = |x: i32| -> i32 { x * 2 };
In many cases, the compiler has enough information to infer the type of a closure. In that case, the programmer may choose not to make the type explicit. This doesn't change the behavior of the closure; it's just a different way for the compiler to determine its type.
let double = |x| { x * 2 };
double(1i32); // This compiler can infer double's type from this.
Sorry, I am not being plain.
In that code I quoted above || -> std::process::Child what I mean is is there and practical effect of declaring the return type of the closure?
AFAICT there is not. The std::process::Child is discarded so its type is irrelevant.
But then why bother declaring it? So I am doubting myself, so I am asking.