Generalize 'None==null' enum optimisation.. .. 'Discriminant' trait?


#1

one great part of rust is the way enum/option handles null pointers.

Would it be possible to generalise this mechanism - perhaps a ‘None’ trait to determine if a value is an invalid state (hence inaccessible) or perhaps a more general ‘Discriminant’ trait. (the ‘None’ trait would be like a boolean discriminant).

As well as the ‘null pointer’, there’s the -1 index pattern, (allowing 2^n -1 valid indices instead of 2^n).

One more general case I sometimes use is “negative extents” … a min/max pair which is invalidated by an initial state where min>max.

DXT textures use something similar: a pair of RGB triples is interpreted to mean something else if the values are in ordered max/min instead of min/max (1 transparent value+3 shades, or 4 shades in the block)

I’ve heard that the ‘negative number is =something else’ (e.g. a u31 with top bit=discriminant) is on the way, but I also heard that will be generalised to an n-bit discriminant.

I"m not sure how you’d fit a general system together though.

Would you implement ‘Discriminant’ for an enum ? you’d already relied on the existence of the descriminant to get out access to the values. So it seems like you’d have to declare that ‘before’, … or ‘inside it’ maybe…

Perhaps you could implement a ‘Valid’ or ‘None’ trait for each variant before composing them into an enum… (The other post about creating an ADT as a T1|T2|T3… was rather interesting.) Perhaps the order would handle any overlap of representations… the first non-invalid value encountered is taken, but it would have to warn you about shadowing

I realise we can still do what we’d do in C++ … create an encapsulated type with unsafe code to deal with these cases.

a related suggestion would be a ‘Sizeof’ trait… where the size of an object can be deduced from some computation on the earliest bytes… together that could give a lot of powerful, safe abstractions… representing CPU instruction set, etc.

playing some syntax ideas - imagine boolean guards written in the enum…

enum Dxt1Block {
    Opaque(Rgb565,Rgb565,[u8,..4]) if self.0.green()>self.1.green(),
    Transparent(Rgb565,Rgb565,[u8,..4])
}

enum OptPtr<T> {
    Some(*T)  if self.0!=0,
    None
}

enum Index<I:Int> {
    Some(I) if self.0!=-1 as I,
    None
}

I suppose you could say if you have this format you must have a guard for each until it falls through to the last, and you know its’ not storing a separate discriminant


#2

I think this is a feature we’ll want, and it’s very obviously a win for lots of things. I’m really not sure how to possibly implement it though. In general, I think you want to tell the compiler either that some bits are unused, and it can use them for a discriminant, or that certain bit patterns are illegal and can be used to represent a variant. I don’t know the best way to do that, though.