Dear Rustaceans,
So RFC 19 introduced the concept of so-called “OIBIT” traits like Send
and Sync
. These are traits which are implemented by default for every struct and enum type if that type contains fields whose types all implement the trait. In other words, a struct is automatically Send
if all of its fields are Send
. Although this RFC has been implemented for some time (thanks @FlaPer87!), most of the details of it remain feature-gated and unstable.
There are two particular details that I would like to discuss changing:
- the name (currently, de facto, OIBIT);
- the syntax to declare an OIBIT trait (currently
impl SomeTrait for ..
).
If you read below you’ll see two suggestions. I sort of like both of them. I’m fishing for feedback on what other people find most intuitive as well as alternative suggestions.
Why change
The acronym “OIBIT”, while quite fun to say, is quite the anachronism. It stand for “opt-in builtin trait”. But in fact, Send
and Sync
are neither opt-in (rather, they are opt-out) nor builtin (rather, they are defined in the standard library). It seems clear that it should be changed.
The declaration syntax impl SomeTrait for ..
also has some clean downsides:
- It’s not particularly obvious what it means.
- Whether a trait is an OIBIT trait or not is really a binary property of the trait, but the syntax suggests it could be made conditional.
- For example, what if I wrote
impl<T:Copy> SomeTrait<T> for ..
– then isSomeTrait<Vec<i32>>
not an OIBIT trait?- Answer: at least according to the compiler, it still is.
- For example, what if I wrote
- The declaration is quite removed from the trait itself.
What I want to change it to
Well, this is where you come in. I’d like some feedback on the best alternative names. Here are some preliminary thoughts:
Structural trait
Rename OIBIT to “structural trait”.
Change the declaration syntax to structural trait
(structural
here would be a contextual keyword; in other words, it is only considered a keyword if the word after it is trait
).
Why: A “structural” type system is one in which the contents of a type matter and not its name. So, for example, Go’s interface subtyping is structural, because a type Foo
implements an interface Bar
if Foo
defines all of the methods in Bar
. It never has to actively declare that it implements Bar
. (In contrast, Java interfaces are nominal, because it’s not enough to have methods with the right names, you have to actively declare that you implement the interface).
Why not: Maybe it’s too jargon-y?
Default trait
As above, change the name and syntax to default trait
.
Why: the trait is implemented “by default” unless you opt out from it. This is actually (more or less) the name that @FlaPer87 adopted internally within the compiler when he was implementing OIBIT support (we actually call them “defaulted traits”). default
is already proposed as a contextual keyword in the specialization RFC.
Why not: seems a bit confusing when you consider the fact that we have a (rather popular) trait named Default
.
FUBAR trait
OK, not a real suggestion, but I totally believe that there are other great keyword choices that will succinctly and (somewhat) clearly express what it going on here. Let your imagination run wild like a horse in a field.