Re: the behavior of opAssign
On Monday, 29 January 2018 at 10:06:23 UTC, Simen Kjærås wrote: On Monday, 29 January 2018 at 09:23:55 UTC, Sobaya wrote: I found a strange behavior. class A { void opAssign(int v) {} } class Test { A a; this() { a = new A(); // removing this causes compile error. a = 3; // cannot implicitly convert expression `3` of `int` to `A` } } void main() { // this is allowed. A a; a = 3; } The first assignment in the constructor isn't actually a call to opAssign, it's a constructor call. In the same way, this will not compile: A a = 3; Also, since classes are reference types, you will need to construct an instance before assigning an int to it. The code in your main() will crash at runtime because the 'this' reference is null inside opAssign. -- Simen I have not read https://dlang.org/spec/class.html In 15.9, there is an explanation about it. Sorry. -- Sobaya
Re: the behavior of opAssign
On Monday, 29 January 2018 at 09:23:55 UTC, Sobaya wrote: I found a strange behavior. class A { void opAssign(int v) {} } class Test { A a; this() { a = new A(); // removing this causes compile error. a = 3; // cannot implicitly convert expression `3` of `int` to `A` } } void main() { // this is allowed. A a; a = 3; } The first assignment in the constructor isn't actually a call to opAssign, it's a constructor call. In the same way, this will not compile: A a = 3; Also, since classes are reference types, you will need to construct an instance before assigning an int to it. The code in your main() will crash at runtime because the 'this' reference is null inside opAssign. -- Simen
Re: the behavior of opAssign
On Monday, January 29, 2018 09:23:55 Sobaya via Digitalmars-d-learn wrote: > I found a strange behavior. > > class A { > void opAssign(int v) {} > } > > class Test { > A a; > this() { > a = new A(); // removing this causes compile error. > a = 3; // cannot implicitly convert expression `3` of > `int` to `A` > } > } > > void main() { > // this is allowed. > A a; > a = 3; > } > > Is it a compiiler's bug? I don't think so. The first "assignment" is actually initialization, not assignment. opAssign is for assigning to a value that was already initialized. - Jonathan M Davis
the behavior of opAssign
I found a strange behavior. class A { void opAssign(int v) {} } class Test { A a; this() { a = new A(); // removing this causes compile error. a = 3; // cannot implicitly convert expression `3` of `int` to `A` } } void main() { // this is allowed. A a; a = 3; } Is it a compiiler's bug?
Strange behavior with opAssign and static if
Hi, I have a template structure Decimal which is used in a OrderDb structure. The opAssign method in Decimal leads to strange behavior in the function execute(); The function execute stores the values of OrderDb in a variant array. Decimals value should be stored as strings. There is a static if for this condition. There is a compilation error for the line arr[i] = __traits(getMember, struc, member); - function.main.OrderDb.opAssign (OrderDb p) is not callable using argument types () This compilation error disappears if I remove the opAssign method in Decimal. How can the opAssign of Decimal influence the code path for a non decimal field? Kind regards André ---code--- import std.traits: isInstanceOf; import std.variant; struct Decimal(int precision, int scale){ void opAssign(T)(T d) if (isInstanceOf!(Decimal, T)){} string toString(){return 10.22;}; } struct OrderDb{ string orderId; Decimal!(10,2) amount; } void main(){ execute(OrderDb()); } void execute(T)(T struc){ Variant[] arr = new Variant[](2); foreach (i, member;__traits(allMembers, T)){ static if (isInstanceOf!(Decimal, typeof(__traits(getMember, struc, member{ // Store decimals as string arr[i] = (__traits(getMember, struc, member)).toString(); } else { // Store other values with their types arr[i] = __traits(getMember, struc, member); } } }
Re: Strange behavior with opAssign and static if
__traits(allMembers) gives you *all* members, including methods (even implicit). As soon as you define opAssign for your Decimal, it gets defined for OrderDb too, and then you try to assign to it :) What you need is something like this: void execute(T)(T struc){ Variant[] arr = new Variant[](2); foreach(i, member; struc.tupleof) { static if (isInstanceOf!(Decimal, typeof(member))){ // Store decimals as string arr[i] = member.toString(); } else { // Store other values with their types arr[i] = member; } } }
Re: Strange behavior with opAssign and static if
Thanks a lot! This works great. Am 08.02.2014 14:27, schrieb Stanislav Blinov: __traits(allMembers) gives you *all* members, including methods (even implicit). As soon as you define opAssign for your Decimal, it gets defined for OrderDb too, and then you try to assign to it :) What you need is something like this: void execute(T)(T struc){ Variant[] arr = new Variant[](2); foreach(i, member; struc.tupleof) { static if (isInstanceOf!(Decimal, typeof(member))){ // Store decimals as string arr[i] = member.toString(); } else { // Store other values with their types arr[i] = member; } } }