Idea: #[zst] on enums with no-data variants?

For example:

enum Variants {
    One(u8),
    #[zst]
    Zero,
}

and if there is a value on the #[zst] variant or more than 1 #[zst] variant then the compiler panics?

For example, if there is 1 #[zst] in a enum of 3,

enum Status {
   #[zst]
   InProgress,
   Ready(Fix),
   ToDo(Issued),
}

then that will be represented as zero-sized and untagged. The others will have tags.

Enums always take the same amount of space in memory; they do not change size based on what case is currently active (some of the bytes just get treated as padding instead). So saying “this case should be zero bytes and untagged” (a) means you can’t look at an enum value and tell if it’s in that case (since you said “untagged”), and (b) does absolutely nothing to change the overall size of an enum value.

You could have a different hypothetical language feature with “unsized enums” represented with fat pointers, where the metadata part of the pointer stored the tag. But even then it would be a tag and not a size, because otherwise you wouldn’t be able to differentiate between two cases whose payloads have the same size.

7 Likes

I agree, differentiation would be required. Perhaps it would work only for enums with sizes below 3? As Option<T> can be treated simply as a T. Perhaps we could have that for other enums?

This is only true for particular types, not all types T. In general, Option<T> may have to have a tag and therefore be bigger than T.

Perhaps we could have that for other enums?

As an optimization, other enums do get exactly the same treatment as Option.

6 Likes