Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow empty structs with braces. #147

Closed
wants to merge 2 commits into from
Closed

Allow empty structs with braces. #147

wants to merge 2 commits into from

Conversation

mahkoh
Copy link
Contributor

@mahkoh mahkoh commented Jun 30, 2014

No description provided.

@bstrie
Copy link
Contributor

bstrie commented Jun 30, 2014

What is the advantage of saying let x = Foo{}; instead of let x = Foo;?

@mahkoh
Copy link
Contributor Author

mahkoh commented Jun 30, 2014

@bstrie: You currently have to write

struct X;
struct Y {
    y: int
}

And you cannot write

struct X {
}

I think this is very annoying. I agree that you might want to keep the version with the ;.

@sinistersnare
Copy link

+1 Whenever i see let x = X; I do a double take, and then remember that X is an empty struct, with this, it might help the ambiguity created in my brain. I guess my brain thinks its an enum for a moment.

let x = X;

let x = X {}

I definitely like the second better. But am fine with both in the end I guess.

@sfackler
Copy link
Member

+1 The current behavior is pretty weird. When I'm working on something, I'll frequently start out with an empty struct and add fields as I need them.

@lilyball
Copy link
Contributor

👎 we explicitly removed the ability to say struct X {} a while back, in the interests of only having one way to write the struct definition. And Foo{} is disallowed in the interests of instantiation-should-follow-declaration.

I also see no benefit to Foo{}. struct Foo; is a type Foo with a single value Foo, and so using Foo as the value makes sense. Foo{} as the value suggests it's constructing something that it's not; all uses of the value Foo are indistinguishable from each other (and in fact it's a zero-sized value). It's equivalent to ().

@mahkoh
Copy link
Contributor Author

mahkoh commented Jun 30, 2014

@kballard: Can you link to the discussion where you decided to disallow struct X { }? I can imagine that the discussion was influenced by the inability to write if x == X { } { ... }.

@nrc
Copy link
Member

nrc commented Jun 30, 2014

+1 to this proposal, I found this weird when I was learning Rust.

@kballard to clarify, you mean the values are indistinguishable at runtime? Two different, empty, struct values of different types (say Foo and Bar) would be statically distinguishable by their types, right?

@lilyball
Copy link
Contributor

@mahkoh Where I decided it? I didn't decide it. And I don't have the link offhand, but I encourage you to git blame the code or look through the commits to see where the code that prevents Foo{} or struct Foo{} was added.

Obviously without a citation I don't have proof, but my recollection is that struct Foo{}; was disallowed purely in the interests of not having more than one way to write a definition (a few other duplicate constructs were disallowed at the same time), and Foo{} as a value is disallowed because values are always constructed in a way that mirrors their declaration; a struct Foo(int,int) is constructed like Foo(1,2) rather than Foo{1,2}, enums are similarly constructed like that, enums that have named fields (which IIRC was feature-gated quite a while back, not sure if it even still exists) were constructed like braced structs (e.g. Foo{a: 1, b: 2}), etc. The ambiguity around if x == X { } { ... } was never even a consideration. I don't think anyone even recognized the existence of that ambiguity at the time this decision was made.

@lilyball
Copy link
Contributor

@nick29581 Two values of type Foo (where Foo is defined struct Foo;) are completely indistinguishable. I'm not talking about two separate nullary structs, as that isn't relevant to any discussion about whether the value syntax should be Foo or Foo{}.

@mahkoh
Copy link
Contributor Author

mahkoh commented Jun 30, 2014

Where I decided it?

By "you" I meant to group of people you referred to here:

we explicitly removed the ability to say


I don't think anyone even recognized the existence of that ambiguity at the time this decision was made.

Isn't it this issue? rust-lang/rust#5167

@emberian
Copy link
Member

That is only struct literals in expression position. There was never an ambiguity with items.

@bstrie
Copy link
Contributor

bstrie commented Jul 1, 2014

I'm a bit confused by this proposal. Let's talk about struct literals first. I would find it very strange to see anyone prefer this:

let x = Foo{};

...over this:

let x = Foo;

As though Rust code isn't noisy enough!

In the interest of having Only One Way To Do It, we forbade the useless brackets on struct literals a long time ago. This used to be a syntax ambiguity, true, but that was just galvanizing the existing urge to "bless" the form that everyone was using anyway.

Finally, in an effort to further simplify, we then forced the declaration of field-less structs to adopt the same form, by forbidding empty brackets. This was not motivated by ambiguity at all, just consistency. However, this latter restriction is definitely capable of raising eyebrows when paired with the empty trait definitions, empty impl blocks, and empty functions, all of which just use empty brackets.

I would ask the author to please clarify what is being proposed here. Do you want to allow the brackets in declarations, and also forbid the bracket-less form? As a separate concern, do you want to allow the brackets in literals, and also forbid the bracket-less form?

@liigo
Copy link
Contributor

liigo commented Jul 1, 2014

+1 for
2014年7月1日 上午5:34于 "Nick Cameron" [email protected]写道:

+1 to this proposal, I found this weird when I was learning Rust.

@kballard https://github.com/kballard to clarify, you mean the values
are indistinguishable at runtime? Two different, empty, struct values of
different types (say Foo and Bar) would be statically distinguishable by
their types, right?


Reply to this email directly or view it on GitHub
#147 (comment).

@gsingh93
Copy link

gsingh93 commented Jul 1, 2014

+1.

@bstrie I definitely prefer the first. As soon as I see it, I know we're initializing a struct with no members. I've associated the {} after an identifier with initializing a struct. When I see the second example I need to think about what's going on because I don't have the {} association.

@bstrie
Copy link
Contributor

bstrie commented Jul 1, 2014

@gsingh93, your perception appears to be mistaken. It is impossible to initialize a struct with no members, because a struct with no members has zero size at runtime. It is an illusion, it does not exist!

@gsingh93
Copy link

gsingh93 commented Jul 1, 2014

@bstrie It's an illusion that makes things easier to read. Not having {} or having {} doesn't tell me anything about the size of the struct, so I'm going to go with the one that's more familiar.

@lilyball
Copy link
Contributor

lilyball commented Jul 1, 2014

@gsingh93 What do you mean, more familiar? With a nullary struct definition struct Foo;, the Foo token is a value. It is in fact the sole value that inhabits the Foo type, just as () is the sole value that inhabits the () type. Foo{} suggests that there's some sort of value construction or initialization going on, and there isn't.

In fact, I can't think of any way in which

struct Foo;

is different than

enum Foo {
    Foo
}

and yet nobody is clamoring for enum values to require {} when they're used.

@gsingh93
Copy link

gsingh93 commented Jul 1, 2014

@kballard You have a point, but if I define something as a struct, I would like to use it with the same syntax as I use for other structs. That includes structs that have no members and structs that have some members. I don't care about the size of the struct or what the compiler considers the struct to be. To me, the programmer, I declared a struct. Thus, I would like to use struct syntax.

@gsingh93
Copy link

gsingh93 commented Jul 1, 2014

Foo{} suggests that there's some sort of value construction or initialization going on, and there isn't.

Does it actually matter whether the programmer thinks there is some sort of initialization or construction going on here? If not, then I'm fine with sending the message that there is (even if that is false) and having the consistent {} syntax.

@lilyball
Copy link
Contributor

lilyball commented Jul 1, 2014

@gsingh93 But Foo{} is not "struct syntax". It is trivially provably not "struct syntax" by virtue of the fact that struct Foo; doesn't use it. Neither does struct Foo(int, int);.

Similarly, if you turn on the struct_variants feature gate, then Foo{a: 3, b: 4} could actually be initializing an enum, even though most enums are just Foo or Foo(1,2).

Your insistence on thinking of Foo{} as "struct syntax" and thinking of all structs as needing to be initialized with the same "struct syntax", despite ample evidence to the contrary, is why you are insisting on Foo{} being how you initialize a nullary struct. You need to let go of that incorrect notion.

FWIW, Foo() makes just as much sense as Foo{} for struct Foo; nullary struct, and yet nobody is proposing that syntax.

@nrc
Copy link
Member

nrc commented Jul 1, 2014

@kballard The RFC is proposing struct Foo{} as the syntax for empty structs, so the Foo {} syntax follows. The only reason the syntax is as it is today is because 'we' designed it that way, so I think you are incorrect to argue like this is some natural way of doing things.

One could also argue for struct Foo() syntax, probably no-one has because tuple-structs are not widely used.

In the end, the choice here comes down to trading off consistency - either you want a struct with 0 fields to be consistent with a struct with n fields where n > 0 (and also consistent with C/C++) or you want consistency with enum variants. You've expressed your opinion on which kind of consistency you prefer and @gsingh93 and others have expressed a different opinion, I don't think either opinion is more correct than the other.

@bstrie (and @mahkoh) my understanding of the RFC (which should be clarified in the RFC itself) is that both the declaration and the literal forms should use {}. Whether to also allow the form without the braces is left as an unresolved question (it should be moved to that section in the RFC). In the interests of only allowing one way to do things I would vote for not allowing it. A further unanswered question is whether we should allow nullary tuple-structs, i.e., allow struct Foo(). That should also be added to the RFC. A drawback as @kballard points out is that we lose consistency with enum variants, that should be added to the drawbacks section.

@nrc
Copy link
Member

nrc commented Jul 1, 2014

And a clarification, if regular structs were the only data structure in Rust, then I think this RFC would be a clear win for consistency. However, they aren't, and we want consistency with tuple-structs and enum variants. We also strive to only have one way to express a concept in Rust code, which seems to preclude having both ways, so we have to make a choice of which kind of consistency is most important.

My personal thought is that the common case here is structs with n fields and we should try to be consistent between n=0 and n>0. But I can see the point of view, that reducing the number of ways to do something or reducing noise or having consistency with enum variants (which are semantically equivalent) is more important.

@bstrie
Copy link
Contributor

bstrie commented Jul 1, 2014

The consistency argument is a wash. Either way you're going to be inconsistent with something. In light of that, I prefer the form that will result in less noise. -1 to this.

@glaebhoerl
Copy link
Contributor

I was going to say the same thing @bstrie said.

@mahkoh
Copy link
Contributor Author

mahkoh commented Jul 1, 2014

@bstrie

I would ask the author to please clarify what is being proposed here. Do you want to allow the brackets in declarations, and also forbid the bracket-less form? As a separate concern, do you want to allow the brackets in literals, and also forbid the bracket-less form?

I'm mostly interested in the point mentioned by @sfackler above: Being able to write struct X { } when you're not yet sure what fields X will have. Let me explain why I think that there should be more than one way to use empty structs:

Consider a math library which contains operators and points with up to 3 coordinates.

trait BinaryOperator {
    fn apply(&self, a: int, b: int) -> int;
}

struct Plus;

impl BinaryOperator for Plus {
    fn apply(&self, a: int, b: int) -> int {
        a + b
    }
}

trait Point { }

struct Point0D();
struct Point1D(f64);
struct Point2D(f64, f64);
struct Point3D(f64, f64, f64);

impl Point3D {
    fn project(self, n: uint) -> Box<Point> {
        let Point3D(x, y, _) = self;
        match n {
            0 => box Point0D()     as Box<Point>,
            1 => box Point1D(x)    as Box<Point>,
            2 => box Point2D(x, y) as Box<Point>,
            _ => box self          as Box<Point>,
        }
    }
}

Plus and Point0D() have little in common. Plus represents an abstract concept while Point0D() is a container with only one possible state. These are different concepts and the fact that both end up being treated like () by the compiler plays no role from this high level perspective. Structs are already an overloaded concept in rust since they can be used as containers with fields and named tuples. Why would you suddenly remove this distinction just because after compilation the type has size 0?

I do agree that "instantiation-should-follow-declaration", that is, structs declared ;, (), {} should only be instantiated ;, (), { } respectively.

@glaebhoerl
Copy link
Contributor

If the idea is not to force empty structs to be declared and used with { }, but to merely allow them to be declared as either of Struct, Struct(), or Struct { }, with use sites required to follow the same syntax, then I'm not necessarily opposed, though I'm also not necessarily convinced of the utility of having three different syntaxes for the same relatively uncommon construct.

@bstrie
Copy link
Contributor

bstrie commented Jul 1, 2014

I am opposed to TIMTOWTDI. Adding in new syntaxes for the same operation can be done backward-compatibly later.

@lilyball
Copy link
Contributor

lilyball commented Jul 1, 2014

If the idea is not to force empty structs to be declared and used with { }, but to merely allow them to be declared as either of Struct, Struct(), or Struct { }

That sounds very confusing. 3 different types of unit structs? And you have to remember which variant of unit struct it was in order to initialize it?

@mahkoh
Copy link
Contributor Author

mahkoh commented Jul 1, 2014

And you have to remember which variant of unit struct it was in order to initialize it?

Not more confusing than having to remember the names of the fields of non-empty structs.

@mahkoh
Copy link
Contributor Author

mahkoh commented Jul 1, 2014

@cmr: You are denying that "instantiation-should-follow-declaration" played a role in the decision to disallow struct X { }? If not then why are you saying that the ambiguity didn't indirectly influence the declaration syntax via the instantiation syntax?

@emberian
Copy link
Member

emberian commented Jul 1, 2014

rust-lang/rust#7981

Consistency was the only consideration.

On Tue, Jul 1, 2014 at 1:10 PM, mahkoh [email protected] wrote:

@cmr https://github.com/cmr: You are denying that
"instantiation-should-follow-declaration" played a role in the decision to
disallow struct X { }? If not then why are you saying that the ambiguity
didn't indirectly influence the declaration syntax via the instantiation
syntax?


Reply to this email directly or view it on GitHub
#147 (comment).

http://octayn.net/

@mahkoh
Copy link
Contributor Author

mahkoh commented Jul 1, 2014

@cmr: That issue doesn't even talk about forbidding struct X { }. The first time forbidding a specific struct syntax is mentioned is on September 20th by @kballard:

I agree with @alexcrichton. struct A; makes sense to leave as-is, everything else should be disallowed.

On the same day @sfackler comments:

It'd also be nice if struct Foo {} were legal. Is there a good reason that the compiler specifically forbids it?

When was this forbidden? For what reasons was ; chosen over { }? The issue sheds no light on these questions.

The comment is followed up by:

Foo { } as an expression literal is ambiguous in the parser

So unless this was done on the very same day, this issue, if not completely unrelated to the removal of struct X { }, shows that the choice ; over { } was because of the ambiguity.

Indeed, on September 19th @alexcrichton writes

This doesn't completely close the issue because struct A; is still allowed

It appears to me that @alexcrichton realized that the choice ; over { } was driven by wanting one consistent way to declare and instantiate structs and the ambiguity.

@pnkfelix
Copy link
Member

pnkfelix commented Jul 2, 2014

One advantage of making the zero-field struct syntax consistent with the non-zero one (for both the struct item as well as the construction expression forms) is that macro_rules that expand into those forms will be able to properly handle the zero-field situation without special case code.

A concrete example:

#![feature(macro_rules)]

macro_rules! twos { ( $S:ident $($x: ident),* ) => { $S { $( $x: 2i ),* } } }

#[deriving(Show)] struct A { x: int, y: int }
#[deriving(Show)] struct B;

pub fn main() {
    let a = twos!(A x, y);

    // The below does not work, since it expands into illegal syntax `B { }`.
    // let b = twos!(B);
    println!("Hello World: {}", a);
}

(caveat: the above example is an easy strawman to tear apart; i.e. "why would you ever write twos!(B)", but that is missing the point: one would think, based on uniformity, that it should work.)

So, if we care about that (I know I do; not sure about other people), then we should consider making the change proposed here.

@glaebhoerl
Copy link
Contributor

@pnkfelix That's a reasonable justification, but I wouldn't want to force the noisier syntax on all "normal" code just to make macros work better. I'd be fine with having it optional, kind of like trailing commas.

Also, couldn't you construct a similar example for tuple structs?

@lilyball
Copy link
Contributor

lilyball commented Jul 2, 2014

@pnkfelix Macros can handle the case anyway, by using $(..),+ for the normal case and a separate matcher for the zero-argument case.

#![feature(macro_rules)]

macro_rules! twos {
    ( $S:ident $($x: ident),+ ) => { $S { $( $x: 2i ),* } };
    ( $S:ident ) => { $S };
}

#[deriving(Show)] struct A { x: int, y: int }
#[deriving(Show)] struct B;

pub fn main() {
    let a = twos!(A x, y);

    // The below works just fine
    let b = twos!(B);
    println!("Hello World: {}", a);
    println!("It works: {}", b);
}

@pnkfelix
Copy link
Member

pnkfelix commented Jul 2, 2014

@kballard that sort of workaround is what I meant when I said "without special case code" in my summary.

But yes, that is a way to get around the problem, and maybe it is acceptable to macro developers.

@pnkfelix
Copy link
Member

pnkfelix commented Jul 3, 2014

@glaebhoerl I suppose one could construct a similar argument for tuple structs ... for some reason I differentiate between unit and tuples, so that in my head zero-tuples just do not exist, and thus I find it easier to accept that likewise zero-tuple structs do not exist, and thus a macro that expands into a tuple struct is simply going to need to take >= 1 argument.

But that is really just roundabout post-hoc justification for my position above.

@pnkfelix
Copy link
Member

pnkfelix commented Jul 3, 2014

(and in fact, I just remembered a case where I do mentally equate unit and zero-tuples, so just ignore what I said above.)

@o11c
Copy link
Contributor

o11c commented Jul 4, 2014

I would like to only use struct Foo; to refer to opaque C structs. If a struct (or enum variant) is actually known to be empty, I'd prefer to require the {} in expressions. If our separation is between opaque structs and empty ones, then () should probably be like {}.

@lilyball
Copy link
Contributor

lilyball commented Jul 4, 2014

struct Foo; is not an opaque struct in Rust. We don't really have the concept. In fact, it's definitively not an opaque struct, because with an opaque struct, there are zero values that inhabit the type, whereas with struct Foo; there is one value that inhabits it (and that value is Foo).

Note that an opaque struct is one where the only way you can use it is via a pointer. This is why any type with values is not an opaque struct, as you can use those values directly.

The only way we have to express a type with no inhabiting values is to use an enum with no variants, e.g. enum Foo {}. IIRC libc::c_void used to be defined this way, but right now it apparently actually has two "private" variants in order to allow it to be #[repr(u8)], because apparently a void pointer needs to be represented in LLVM bit code as a i8* in order to be recognized as the void pointer type. But that's an implementation detail; in theory, it would be defined as pub enum c_void {}.

@pnkfelix
Copy link
Member

pnkfelix commented Aug 4, 2014

By the way, with regards to @sfackler 's point that:

When I'm working on something, I'll frequently start out with an empty struct and add fields as I need them

my current approach to dealing with this is to write such prototype structs this way:

struct Foo {
  _dummy_placeholder: ()
}

This way it is super-clear that I intend to put more fields in later, that this code is just still under-development.

So I am not super-convinced that the "let me write braces so I have a place to put things later" holds all that much water.

@nikomatsakis
Copy link
Contributor

@mahkoh can you collect what you view as the best arguments from this thread and update the rfc?

@rkjnsn
Copy link
Contributor

rkjnsn commented Aug 5, 2014

+1 for allowing braces on both declarations and literals.

@mahkoh
Copy link
Contributor Author

mahkoh commented Aug 5, 2014

updated

@lilyball
Copy link
Contributor

lilyball commented Aug 5, 2014

Drawbacks

None

Well that's certainly not true. You're providing an extremely biased view here.

@liigo
Copy link
Contributor

liigo commented Aug 6, 2014

What's that if any?
Sent using CloudMagic
On 周三, 8月 06, 2014 at 5:26 上午, Kevin Ballard [email protected] wrote:
Drawbacks

None

Well that's certainly not true. You're providing an extremely biased view here.

—Reply to this email directly or view it on GitHub.

@lilyball
Copy link
Contributor

lilyball commented Aug 6, 2014

@liigo There has been a lot of discussion in this PR on this topic.

@pnkfelix
Copy link
Member

pnkfelix commented Aug 6, 2014

This RFC is not all that well fleshed out to begin with.

  1. Its so-called "detailed design" is the single line:

    Replace ; by { } everywhere.

    I am all for one-line language changes when they make sense, but this is not an instance of that.

    In particular, multiple people (bstrie, nrc) asked for updates regarding struct declarations versus struct expressions, but no such updates were incorporated into the detailed design.

  2. When asked to collect the best arguments from the comment thread, the author chose to only put in the arguments in favor of the RFC, and summarized the arguments against the RFC by replacing "Drawbacks: None that I know of." with "Drawbacks: None", ignoring the points made against the RFC in the comment thread.

The above observations lead me to believe that this particular RFC is not going to yield a usable document for people to refer back to in the future. If we accepted such a document, it would represent a failure in the RFC process, regardless of how the core team may feel about the spirit of this suggested change.


The core team was already going to close this RFC (see meeting minutes). I just wanted to write down explicitly that I would argue in favor of closing this particular RFC pull request based on the observations above.


# Unresolved questions

TIOOWTDI (with a majority in favor)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I am guessing that this is meant to denote "There Is Only One Way To Do It." (But in that case, why is it in the "Unresolved Questions" section rather than "Drawbacks" section? And really, the point needs to be explicitly elaborated.)

Acronyms like this are appropriate for SMS messages and twitter; not for a documents like this, especially since some of the core team members did not know what this meant (and I didn't figure out a guess for it until well after seeing their conversation).

@mahkoh
Copy link
Contributor Author

mahkoh commented Aug 6, 2014

@kballard: I read @nikomatsakis request so that I should provide the best arguments for the change, not against.

If it's not going to be accepted then that it doesn't matter anyway. It's nothing more than bikeshedding and struct X { _dummy: (), } is good enough.

@pnkfelix: People used such acronyms in this thread and nobody complained about them.

But in that case, why is it in the "Unresolved Questions" section rather than "Drawbacks" section?

Because the RFC say "Allow {}", not "Allow only {}".

@mahkoh mahkoh closed this Aug 6, 2014
@huonw
Copy link
Member

huonw commented Aug 6, 2014

People used such acronyms in this thread and nobody complained about them.

The actual RFC text needs to be more formal and more detailed than just general discussion.

@pnkfelix
Copy link
Member

pnkfelix commented Aug 6, 2014

@mahkoh

People used such acronyms in this thread and nobody complained about them.

I do not attempt to go through and edit everyone's comments in the dialogue on an RFC; where the expectation is that one has read the preceding dialogue before a given comment (and thus an ad-hoc acronym can at least be understandable). But I cannot afford to take that attitude on an RFC, where the document is meant to live on independently from the comment thread here.

But in that case, why is it in the "Unresolved Questions" section rather than "Drawbacks" section?

Because the RFC say "Allow {}", not "Allow only {}".

The expansion of "TIOOWTDI" into "There is only one way to do it" is not a question. (It is also not a drawback, unless you apply a healthy amount of context to one's interpretation, which is what I was trying to do when I wrote my comment above.)


I do not know your background, in terms of whether english is your native language, etc, so please do not take offense at the following bullet points. I just want to set the record straight in terms of what sorts of phrases are actually sensible for each part of an RFC:

  • An example of a question would be

    "Do we further restrict the syntax to only allow struct Foo { }, rather than allowing both struct Foo; and struct Foo { }, as is currently proposed in the RFC?"

  • An example of a drawback would be

    "Allowing both of the syntaxes struct Foo { } and struct Foo; as denotations for the same item declaration violates the principle of "There Is Only One Way To Do It (TIOOWTDI)", which Rust tries to adhere to."

@mahkoh
Copy link
Contributor Author

mahkoh commented Aug 6, 2014

Please don't waste more time on this bikeshedding.

@liigo
Copy link
Contributor

liigo commented Aug 7, 2014

@pnkfelix

"Allowing both of the syntaxes struct Foo { } and struct Foo; as denotations for the same item declaration violates the principle of "There Is Only One Way To Do It (TIOOWTDI)", which Rust tries to adhere to."

You are right. But why we have two ways now?
struct Foo; looks weird IMO, like a C struct pre-declaration.

On function call, we allow empty-parenthesis: f(), instead of f;.
And function definition allows empty braces.

@huonw
Copy link
Member

huonw commented Aug 7, 2014

@liigo this whole RFC is about changing the empty struct declaration syntax, and is now closed (without being merged), i.e. please read the RFC and rest of the discussion. (Also, note that @pnkfelix was just rephrasing text as an example of how an RFC should be written, not adding any new content about the proposed changes.)

Please don't waste more time on this bikeshedding.

@pnkfelix was trying to constructively offer assistance on what an RFC should include and how it should be written (since it is designed to be a reference document for posterity); not wasting time on bikeshedding.

wycats pushed a commit to wycats/rust-rfcs that referenced this pull request Mar 5, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.