Thread overview | ||||||||||
---|---|---|---|---|---|---|---|---|---|---|
|
February 05, 2014 opAssign and template class | ||||
---|---|---|---|---|
| ||||
Please consider this: http://dpaste.dzfl.pl/dc4a3c29e57f What is my mistake ? Thanks ... |
February 05, 2014 Re: opAssign and template class | ||||
---|---|---|---|---|
| ||||
Posted in reply to dbjdbj | On Wednesday, 5 February 2014 at 10:33:08 UTC, dbjdbj wrote: > > Please consider this: http://dpaste.dzfl.pl/dc4a3c29e57f > > What is my mistake ? > > Thanks ... You cannot overload identity assignment for classes. It's a language construct that rebinds a reference and cannot be overridden. Such opAssign overloading is only possible for structs. See http://dlang.org/operatoroverloading.html#Assignment. |
February 05, 2014 Re: opAssign and template class | ||||
---|---|---|---|---|
| ||||
Posted in reply to Stanislav Blinov |
>
> You cannot overload identity assignment for classes. It's a language construct that rebinds a reference and cannot be overridden. Such opAssign overloading is only possible for structs.
>
> See http://dlang.org/operatoroverloading.html#Assignment.
I need to be able to implement "=" operator so that this works:
auto x_ = new X(), x2 = x_ ;
objects)alive needs to be 2 after.
Thanks ...
|
February 05, 2014 Re: opAssign and template class | ||||
---|---|---|---|---|
| ||||
Posted in reply to dbjdbj | On Wednesday, 5 February 2014 at 12:29:11 UTC, dbjdbj wrote:
> I need to be able to implement "=" operator so that this works:
>
> auto x_ = new X(), x2 = x_ ;
>
> objects)alive needs to be 2 after.
>
> Thanks ...
You can't. Classes are reference types. This just doesn't make sense: x2 = x_; does not create any new objects.
|
February 05, 2014 Re: opAssign and template class | ||||
---|---|---|---|---|
| ||||
Posted in reply to Stanislav Blinov |
>
> You can't. Classes are reference types. This just doesn't make sense: x2 = x_; does not create any new objects.
*object_alive* is what I mentioned, not object_create
therefore it does "make sense" ... so here it is again:
auto x_ = new X() , // created:1 , alive: 1
x2 = x_ ; // created:1 , alive: 2
I tried (in all of my D innocence) to implement simple but effective counter from C++ side of the "wall" ... using the CRTP idiom ...
|
February 05, 2014 Re: opAssign and template class | ||||
---|---|---|---|---|
| ||||
Posted in reply to dbjdbj | On Wednesday, 5 February 2014 at 13:38:08 UTC, dbjdbj wrote: > >> >> You can't. Classes are reference types. This just doesn't make sense: x2 = x_; does not create any new objects. > > *object_alive* is what I mentioned, not object_create Yes, but in your implementation you intend to increment both counters in opAssign. > therefore it does "make sense" ... so here it is again: > > auto x_ = new X() , // created:1 , alive: 1 > x2 = x_ ; // created:1 , alive: 2 > > I tried (in all of my D innocence) to implement simple but effective counter from C++ side of the "wall" ... using the CRTP idiom ... You just cannot reliably count references to class objects in D (at least, yet, see the ongoing discussions: http://forum.dlang.org/thread/lcrue7$1ho3$1@digitalmars.com, http://forum.dlang.org/thread/grngmshdtwqfaftefhky@forum.dlang.org). For non-class objects, there is a library implementation, std.typecons.RefCounted. With it, you can roll something similar: import std.stdio; import std.typecons; struct Counter(T) if (!is(T == class)) { @disable this(this); @disable void opAssign(ref Counter); private static int objectsCreated_ = 0; private T x_; this(T x) { x_ = x; ++objectsCreated_; } static int getObjectsCreated() { return objectsCreated_; } @property ref auto get() inout { return x_; } alias get this; } auto counter(T,Args...)(ref auto Args args) if (!is(T == class)) { return RefCounted!(Counter!T)(T(args)); } @property auto objectsCreated(O)(ref O o) if (is(O == RefCounted!(Counter!T), T)) { return o.getObjectsCreated(); } @property auto numReferences(O)(ref O o) if (is(O == RefCounted!(Counter!T), T)) { return o.refCountedStore.refCount; } struct X { int v; } struct Y { string s; } void foo(ref const X x) { writefln("%s", x.v); } void bar(ref const Y y) { writefln("%s", y.s); } void main() { auto x_ = counter!X, x2 = x_; writefln("objects created: %s, num references: %s", x_.objectsCreated, x_.numReferences); foo(x_); auto y_ = counter!Y("hello"), y2 = y_; y2.s = "world"; // Modifies y_.s too writefln("objects created: %s, num references: %s", y_.objectsCreated, y_.numReferences); bar(y_); } --- Note that e.g. typeof(x_) is actually RefCounted!(Counter!X). But you cannot do similar for classes, because you cannot guard against escaping references. |
February 05, 2014 Re: opAssign and template class | ||||
---|---|---|---|---|
| ||||
Posted in reply to Stanislav Blinov | Impressive but please next time please use: http://dpaste.dzfl.pl/ ... Depressive is this issue (and some more) since I was sincerely hoping I could live C++ "behind" ... Eh ... |
February 05, 2014 Re: opAssign and template class | ||||
---|---|---|---|---|
| ||||
Posted in reply to dbjdbj | On 02/05/2014 09:37 AM, dbjdbj wrote:> > Impressive but please next time please use: http://dpaste.dzfl.pl/ ... I disagree. dpaste has no association with this newsgroup and can disappear at any time in the future. > > Depressive is this issue (and some more) since I was sincerely hoping I > could live C++ "behind" ... > > Eh ... There is a significant difference between D and C++. In D, classes are reference types (not value types). The equivalent in C++ of what you are trying to do would be overriding the assignment operator for class pointers, which is not possible in C++: // C++ code: X * x_ = new X() , // created:1 , alive: 1 * x2 = x_ ; // created:1 , alive: 2 (not possible!) Same limitation in D... Ali |
Copyright © 1999-2021 by the D Language Foundation