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

“Ephemeral substitution” section confusing? #322

Closed
shelby3 opened this issue Sep 9, 2018 · 6 comments
Closed

“Ephemeral substitution” section confusing? #322

shelby3 opened this issue Sep 9, 2018 · 6 comments

Comments

@shelby3
Copy link

shelby3 commented Sep 9, 2018

https://tutorial.ponylang.org/capabilities/capability-subtyping.html#ephemeral-substitution

The reason is that an ephemeral reference capability is a way of saying "a reference capability that, when aliased, results in the base reference capability".

I surmise literally what you’re trying to say there, but that sentence still lacks coherence even when literally more explicit. Ostensibly you literally mean, “a reference capability that, when aliased, results in the non-ephemeral base reference capability from which the ephemeral capability was derived.”

Yet even that is still confusing because it doesn’t fully help the reader grok intended essence of the reason that ^iso and ^trn can’t be subtypes of themselves.

AFAICT, what you intend to convey is that, “an ephemeral reference capability that, when aliased, doesn’t enable any additional supertypes as compared to the non-ephemeral base reference capability (from which the ephemeral capability was derived) is interchangeable with the said base.”

Perhaps you can devise a way to segment the run-on sentence of mine without losing the key essence of, “doesn’t enable any additional supertypes as compared to the.”


Additionally I can’t find any where in the tutorial where the following promise is fulfilled:

Why do ref^, val^, box^, and tag^ exist if they are interchangeable with their base reference capabilities? It's for two reasons: reference capability recovery and generics. We'll cover both of those later.

I deduce that reason w.r.t. to generics is when the result/return reference is the result of a consume then the result/return reference much be consistently ephemeral A^ regardless of the concrete type the generic type parameter A is instantiated with?


P.S. Additionally not really as a documentation issue. Why every result/return reference can’t be typed as an implicit consume so they’re always ephemeral? Since return values are to never be aliased, what difference would it make since AFAICT the only disposal of a result/return reference is to assign it or discard it? I note the stated requirement for ephemeral types to distinguish new objects returned from constructors from extant objects that have already been bound to an identifier. Does the distinction pertain to some potential compiler optimizations? It’s as if an ephemeral is akin to an r-value in C/C++. Might this be related to the option to use stack allocation with escape analysis instead of allocating everything on the GC heap?

@jemc
Copy link
Member

jemc commented Oct 5, 2018

Regarding the first section of this ticket, I'm having trouble understanding what's missing from the explanation in the tutorial. I know you've given an example replacement sentence, but I personally don't find it to be more specific or helpful than what's currently there. It's probably just a problem with my perspective, and not with your suggestion.


Additionally I can’t find any where in the tutorial where the following promise is fulfilled:

Why do ref^, val^, box^, and tag^ exist if they are interchangeable with their base reference capabilities? It's for two reasons: reference capability recovery and generics. We'll cover both of those later.

Which specific promise isn't fulfilled? Recovery is discussed here and generics are discussed in Chapter 5.

@jemc
Copy link
Member

jemc commented Oct 5, 2018

Why every result/return reference can’t be typed as an implicit consume so they’re always ephemeral? Since return values are to never be aliased

Returning a reference doesn't count as an alias, but there are many examples of non-ephemeral return values. The most common example of a non-ephemeral return value is a "getter", where the object exposes a field by returning it from a "getter" method. Such a field has at least one alias, in the object's field reference, so it is not ephemeral (unless it is of one of the capabilities that is inherently equivalent to its ephemeral counterpart).

@shelby3
Copy link
Author

shelby3 commented Dec 3, 2018

Regarding the first section of this ticket, I'm having trouble understanding what's missing from the explanation in the tutorial. I know you've given an example replacement sentence, but I personally don't find it to be more specific or helpful than what's currently there. It's probably just a problem with my perspective, and not with your suggestion.

I agree that after re-reading my OP, that I was still confused.

I can’t grok the relevance of the cited sentence of the tutorial in the context and also the meaning seems to not make sense, “The reason is that an ephemeral reference capability is a way of saying ‘a reference capability that, when aliased, results in the base reference capability’.”

Can ephemeral types ever be aliased? That sentence seems to imply they can be. I presume an ephemeral reference can only be assigned once and the ephemeral reference can no longer be accessed after it is assigned (or at least so for ^iso). So my presumption is there’s never any aliases of an ephemeral capability typed reference (at least in the case of ^iso).

I do understand that iso and trn can’t be subtypes (i.e. assignable to) ^iso and ^trn respectively, because iso and trn can’t be aliased (because their capabilities are exclusive), i.e. assigning from a non-ephemeral reference to another non-ephemeral reference results in two aliases. Whereas assigning an ephemeral reference to a non-ephemeral references results in only one alias because the ephemeral reference can only be assigned once (i.e. it is consumed when it is assigned). I suggest that is one simple way of stating it that everyone can easily grok. The reader must know that aliasing (in the context of referencing) literally means assigning the reference to another reference so that more than one reference to the same object exists.

So the other ephemeral capabilities can be supertypes of their base capability type from which the ephemeral type originated, because those other base capability types can be aliased. It is that simple. But I still can’t relate the cited sentence of the tutorial to either of these (what I believe to be) more clear explanations. Also I think the term ‘base’ can be misleading because the naive reader might think it means the supertype instead of the type from which the ephemeral type originated. Not every reader will have a verbal IQ at two SD or above.

I hope you improve that section because my IQ is not that low (i.e. probably above the mean for programmers) and so if I am having trouble understanding that sentence, there’s going to be a huge swath of programmers who also won’t. Apologies in advance if I am simply missing an obvious interpretation of that cited sentence. Perhaps you can explain what it means? I do note my verbal scores on SAT where significantly lower than my math and I am suffering a liver dysfunction which affects my mental energy, so perhaps I am mistaken here. I will await your reply.

P.S. I can see that I was still confused about the reason when I wrote the OP, because where for example I wrote the following as quoted, I was just observing that iso and trn are not supertypes of themselves. But that doesn’t really capture the understanding of the reason which I think I have correctly stated in this post.

Perhaps you can devise a way to segment the run-on sentence of mine without losing the key essence of, “doesn’t enable any additional supertypes as compared to the.”

@shelby3
Copy link
Author

shelby3 commented Dec 3, 2018

Why every result/return reference can’t be typed as an implicit consume so they’re always ephemeral? Since return values are to never be aliased

Returning a reference doesn't count as an alias, but there are many examples of non-ephemeral return values. The most common example of a non-ephemeral return value is a "getter", where the object exposes a field by returning it from a "getter" method. Such a field has at least one alias, in the object's field reference, so it is not ephemeral (unless it is of one of the capabilities that is inherently equivalent to its ephemeral counterpart).

Thanks I understand now. Generally stated, can’t implicitly consume an iso or trn reference which is the field of some other object whose lifetime outlives the function because consume requires its input (i.e. base) reference to no longer be in use after the consume (because consume outputs the ephemeral counterpart that can be later assigned). And that requirement is to enforce the exclusive rights of those two capabilities.

Which I also note is related to the reason (i.e. they are exclusive and limitations on aliasing) that those two base capabilities aren’t subtypes of their respective ephemeral counterparts as I explained in my prior post today.

Additionally I can’t find any where in the tutorial where the following promise is fulfilled:

Why do ref^, val^, box^, and tag^ exist if they are interchangeable with their base reference capabilities? It's for two reasons: reference capability recovery and generics. We'll cover both of those later.

Which specific promise isn't fulfilled? Recovery is discussed here and generics are discussed in Chapter 5.

The implied promise to answer the question I cited from the tutorial. I know those tutorial sections exist, but I couldn’t find where within those sections the cited question is answered. I felt like I was on an Easter egg hunt trying to find the answer.

So what is the answer and where is it provided in the tutorial if at all?

@shelby3
Copy link
Author

shelby3 commented Dec 7, 2018

Why do ref^, val^, box^, and tag^ exist if they are interchangeable with their base reference capabilities?

So what is the answer and where is it provided in the tutorial if at all?

I believe I partially answered my own question with an edit I added to my prior post before that one:

[…] i.e. assigning from a non-ephemeral reference to another non-ephemeral reference results in two aliases. Whereas assigning an ephemeral reference to a non-ephemeral references results in only one alias because the ephemeral reference can only be assigned once (i.e. it is consumed when it is assigned).

So apparently there are use cases where even non-exclusive references need to be consumed to make generics work correctly with reference capability recovery?

If that is correct, I suggest stating so in that section of the tutorial instead of leaving some readers hanging with incomplete understanding. And perhaps give a better hint of where to look in the other sections for examples.

EDIT: George Steed’s paper seems to indicate in §3.3.2 Ephemeral Capability Equivalence that those 4 additional ephemeral types are uninteresting. Although he is making some distinction (that I don’t yet understand) between ephemeral modifiers and types.

@jasoncarr0
Copy link
Contributor

Closing via #449

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

No branches or pull requests

3 participants