Why can't None be cloned for a generic Option<T> when T doesn't implement Clone?

As the other answers correctly point ouf, this is due to the way the vec!-macro is implemented. You can manually create a Vec of any Option<T> without requiring T to be Clone:

let bar = std::iter::repeat_with(|| Option::<T>::None).take(size).collect::<Vec<_>>();

This will create size-number of Option::<T>::None and place them in a Vec, which will be pre-allocated to the appropriate size. This works for any T.

If one part can't be cloned, then no parts can be cloned. Think about this from a type perspective: you have a variable called foo of type Option<T>, where T isn't clonable. Sure, None can be cloned, but Some(_) can't, and the type of the variable doesn't tell you which it is. So, from a compile-time perspective, you can't clone the option.

Isn't a None of type T the same as any other None?

Definitely not! Unlike reference-based languages where null is typically implemented as a null-reference, Rust's Option<T> introduces no indirection and stores T inline when the option is Some. Since all enum variants have the same size, the None variant must still occupy at least as much space as T.

Having said that, it is technically true that the None value could be cloned without T being Clone simply because the None variant of the enum doesn't contain the T, it only stores the discriminator and reserves space that could contain T if the variant were to change to Some. But since Rust enum variants are not separate types, a trait bound defined for the enum must cover all variants.

See other answers more detailed explanations and instructions how to create a vector of None values of a non-cloneable Option.