-
-
Notifications
You must be signed in to change notification settings - Fork 608
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
Add hasElaborateCopyConstructor trait #10265
Conversation
Thanks for your pull request and interest in making D better, @edi33416! We are looking forward to reviewing it, and you should be hearing from a maintainer soon.
Please see CONTRIBUTING.md for more information. If you have addressed all reviews or aren't sure how to proceed, don't hesitate to ping us with a simple comment. Bugzilla referencesYour PR doesn't reference any Bugzilla issue. If your PR contains non-trivial changes, please reference a Bugzilla issue or create a manual changelog. Testing this PR locallyIf you don't have a local development environment setup, you can use Digger to test this PR: dub fetch digger
dub run digger -- build "master + dmd#10265" |
static assert(__traits(hasElaborateCopyConstructor, U!S)); | ||
static assert(__traits(hasElaborateCopyConstructor, SPostblit)); | ||
|
||
static assert(!__traits(hasElaborateCopyConstructor, NoCpCtor)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we add a test with a nested struct too?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There is Outer.S
. Am I missing something?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This implementation will return true when __traits(hasElaborateCopyConstructor)
is used with a type that is not a struct. You should probably add some tests to verify that other types like classes or basic types return false for this check.
There's some confusion over what an "elaborate" copy constructor even is. https://dlang.org/phobos/std_traits.html#hasElaborateCopyConstructor That says elaborate means having a postblit. But you say "I think that structures that define a postblit should also be considered to have an elaborate copy constructor" meaning this PR defines it as something else? Putting a trait in the core language means the core language must have a proper definition of it. C++ has no notion of an "elaborate" copy constructor. I confess I have no idea what it should mean and what such a definition would be good for. If "elaborate copy constructor" is a euphemism for "postblit", why not call it "postblit"? I remember back when we were trying to come up with a name for immutable types. People came up with readonly, invariant, etc. When people would ask what readonly or invariant meant, we'd respond with "it means immutable". Finally we got thwacked with a clue-by-four and noticed the obvious - name it "immutable". Didn't have to explain it after that. |
There is postblit, and there is copy constructor. I think the interesting fact is "do I need to run special code to copy this". The reason this should be a trait is because as we've shown, the compiler will use internal logic to determine if it should call a postblit or copy constructor, and it's very hard to reproduce that logic in library. It is critical that library can sample the same condition, otherwise copying mechanics will have strange edge cases in library code. |
So, by my reasoning 'elaborate copy' means "something other than a straight binary copy". I would apply the same terminology to 'elaborate move', 'elaborate construction' (something other than a blit of |
src/dmd/traits.d
Outdated
} | ||
else if (e.ident == Id.hasElaborateCopyConstructor) | ||
{ | ||
return sd.hasCopyCtor || sd.postblit !is null ? True() : False(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Right, compare this to the library solution ;) ... this builds confidence.
The whole naming and documentation issue can be avoided by simply having two traits:
and voila! No confusion, no extra explanation needed, and it's more flexible - the user can decide if he's checking for postblit too or not. |
That's true, but then we also have to be certain that the compiler internally performs exactly |
Remember this may get complicated with concepts like copy ctor overloads, move construction (if it turns out that way), etc... |
Please also check out the updated library PR |
I just checked, and it looks like the old PR... did push? enum hasElaborateCopyConstructor(T) = __traits(hasElaborateCopyConstructor, T); ?? |
The druntime PR provides an alternative to the issue without requiring the |
Why has this stalled? |
@WalterBright @andralex @RazvanN7 can this be merged? This would allow the corresponding druntime PR to move forward. |
@thewilsonator can you help with this? |
0c448c6
to
556ed8a
Compare
I agree. Refactored as @TurkeyMan suggested. @WalterBright @RazvanN7 what do you think? |
It would be cool to unblock dlang/druntime#2780... |
ping the @thewilsonator |
Since the compiler already defines & uses fields named |
I had that thought too, and I agree as long as we can be confident that the proper logic is and will always be the disjunction of those 2 values... so, can we be sure of that? is |
How about the converse - we define |
As a traits? That's this expression: |
I can't add tags such as "blocked" as it quite clearly this is blocking certain c++ std libraries from integrating in the d druntime. |
This is still dangling :( |
As defined in this PR, the two are combined into a new, and pointless, jargon. The next PR will be to split it into two. Just do it as two to begin with, then it doesn't need explaining. |
Or the thing Andrei says...? |
i forked and revived to split the traits #10528 |
Closing in favor of #10528. |
This was requested in this druntime PR.
Exposing this behaviour straight from the compiler has two benefits:
EDIT:
Please note that this trait returnsfalse
for types that have apostblit
. Open question: should it return true?After some further consideration I think that structures that define a
postblit
should also be considered to have an elaborate copy constructor. After all, this is what the library implementation do, so, imho, it would be confusing for the users for the trait to be different.