View mode: basic / threaded / horizontal-split · Log in · Help
September 01, 2008
Static operator overloads (again)
I am trying to translate the following C# code into D

    public class Test
       {
           public string Name;

           public static Test operator +(Test lvalue, Test rvalue)
           {
               if (lvalue == null) { lvalue = new Test(); lvalue.Name = "foo"; }
               if (rvalue == null) { rvalue = new Test(); rvalue.Name = "bar"; }

               Console.Write(lvalue.Name);
               Console.Write(rvalue.Name);

               return rvalue;
           }

       }

void main()
{
   Test T = null;
   Test B = null;
   T += B;
}

Whilst leaving the syntax of main() untouched.
September 01, 2008
Re: Static operator overloads (again)
On Mon, Sep 1, 2008 at 9:11 AM, Giles Bathgate <gilesbathgate@gmail.com>wrote:

> I am trying to translate the following C# code into D
>
>     public class Test
>        {
>            public string Name;
>
>            public static Test operator +(Test lvalue, Test rvalue)
>            {
>                if (lvalue == null) { lvalue = new Test(); lvalue.Name =
> "foo"; }
>                if (rvalue == null) { rvalue = new Test(); rvalue.Name =
> "bar"; }
>
>                Console.Write(lvalue.Name);
>                Console.Write(rvalue.Name);
>
>                return rvalue;
>            }
>
>        }
>
> void main()
> {
>    Test T = null;
>    Test B = null;
>    T += B;
> }
>
> Whilst leaving the syntax of main() untouched.
>
>
Long story short: I really don't think you can.  Operator overloading in D
can only be performed as nonstatic methods of user-defined types.  Since a
virtual method call requires that the object you're calling it on be
non-null (so that you can get the vtable), you can't use overloaded
operators on null references.
September 02, 2008
Re: Static operator overloads (again)
Jarrett Billingsley Wrote:

> Long story short: I really don't think you can.  Operator overloading in D
> can only be performed as nonstatic methods of user-defined types.  Since > a virtual method call requires that the object you're calling it on be
> non-null (so that you can get the vtable), you can't use overloaded
> operators on null references.

But static operator overloads are possible in D.
September 02, 2008
Re: Static operator overloads (again)
Giles Bathgate Wrote:

> But static operator overloads are possible in D.

Example:

public class Test
{
       public char[] Name;

       public static Test opAddAssign(Test value)
       {
               writefln(value.Name);
               //TODO...
       }
}

int Main()
{
       Test t;
       Test b = new Test();
       b.Name = "foo"

       t += b; // Translates to:   Test.opAddAssign(b);

}

The problem with this though is that there is no access to the lvalue t 
this is because t+=b; translates to Text.opAddAssign(b);  I would like to propose a feature that given the operator overload:

public static Test opAddAssign(Test lvalue, Test rvalue)
{
}

then

t += b; 

would translate to: 

Test.opAddAssign(t,b);

I really think this would benefit the language, without breaking anything since the compiler can distinguish between single and double parameter static operator overloads.
September 02, 2008
Re: Static operator overloads (again)
Giles Bathgate wrote:
> Giles Bathgate Wrote:
> 
>> But static operator overloads are possible in D.
> 
> Example:
> 
> public class Test
> {
>         public char[] Name;
> 
>         public static Test opAddAssign(Test value)
>         {
>                 writefln(value.Name);
>                 //TODO...
>         }
> }
> 
> int Main()
> {
>         Test t;
>         Test b = new Test();
>         b.Name = "foo"
> 
>         t += b; // Translates to:   Test.opAddAssign(b);
> 
> }
> 
> The problem with this though is that there is no access to the lvalue t 
> this is because t+=b; translates to Text.opAddAssign(b);  I would like to propose a feature that given the operator overload:
> 
>  public static Test opAddAssign(Test lvalue, Test rvalue)
>  {
>  }
> 
> then
> 
> t += b; 
> 
> would translate to: 
> 
> Test.opAddAssign(t,b);
> 
> I really think this would benefit the language, without breaking anything since the compiler can distinguish between single and double parameter static operator overloads.

I don't particularly think that it would benefit the language. There's 
no difference between a method call and using an operator overload. If 
you find yourself doing a lot of null checks, you might want to check 
out the Null Object pattern.

I don't think that having operator overloads be static is such a bad 
thing, though it prevents you from overloading operators with types. 
(downs has some interesting examples to this effect...)
September 03, 2008
Re: Static operator overloads (again)
Christopher Wright Wrote:

> I don't particularly think that it would benefit the language. There's 
> no difference between a method call and using an operator overload. If 
> you find yourself doing a lot of null checks, you might want to check 
> out the Null Object pattern.

The point is when I write 

t += b;

I don't expect a null reference exception. With operator overloads the only way (that made sense to me) to achieve this was to make the opCatAssign method static, but then my dilemma is that I no longer have an access to the value of t within the opCatAssign method call.
September 04, 2008
Re: Static operator overloads (again)
Giles Bathgate wrote:
> Christopher Wright Wrote:
> 
>> I don't particularly think that it would benefit the language. There's 
>> no difference between a method call and using an operator overload. If 
>> you find yourself doing a lot of null checks, you might want to check 
>> out the Null Object pattern.
> 
> The point is when I write 
> 
> t += b;
> 
> I don't expect a null reference exception. With operator overloads the only way (that made sense to me) to achieve this was to make the opCatAssign method static, but then my dilemma is that I no longer have an access to the value of t within the opCatAssign method call.

On the other hand, what about subclasses? They can't override the 
behavior of an operator overload, if operator overloading uses static 
methods. You're reduced to writing your overloads as:

class Foo
{
	static Foo opAddAssign (Foo left, Foo right)
	{
		return left.addAssign(right);
	}
}

So your proposal eliminates two valid use cases and breaks existing 
syntax and expectations. The only benefit you get is being able to use 
null in an operator overload, which is also an unexpected change from 
the existing system.

Just use the Null Object pattern. It's intended to solve exactly the 
sort of problem you have, and it works with methods as well.
September 04, 2008
Re: Static operator overloads (again)
Christopher Wright Wrote:

> On the other hand, what about subclasses? They can't override the 
> behavior of an operator overload, if operator overloading uses static 
> methods. You're reduced to writing your overloads as:
> 
> class Foo
> {
> 	static Foo opAddAssign (Foo left, Foo right)
> 	{
> 		return left.addAssign(right);
> 	}
> }
> 

I don't understand your example. It was my understanding that static methods cannot be overridden. (there is no vtable entry for a static method)

Maybe you thought that I an requesting for D's implementation of operator overloads to ONLY use static methods?
September 04, 2008
Re: Static operator overloads (again)
On Thu, 04 Sep 2008 13:47:20 +0400, Giles Bathgate  
<gilesbathgate@gmail.com> wrote:

> Christopher Wright Wrote:
>
>> On the other hand, what about subclasses? They can't override the
>> behavior of an operator overload, if operator overloading uses static
>> methods. You're reduced to writing your overloads as:
>>
>> class Foo
>> {
>> 	static Foo opAddAssign (Foo left, Foo right)
>> 	{
>> 		return left.addAssign(right);
>> 	}
>> }
>>
>
> I don't understand your example. It was my understanding that static  
> methods cannot be overridden. (there is no vtable entry for a static  
> method)
>

Indeed, static methods can't be overriden. That's why you end up writing  
something like this to get polymorphism in C#.

> Maybe you thought that I an requesting for D's implementation of  
> operator overloads to ONLY use static methods?

No, but what is the real difference between two, apart from ability to  
pass null pointers which is a bad design anyway? It is redundant. I think  
it should be removed from language at all.
September 05, 2008
Re: Static operator overloads (again)
Giles Bathgate wrote:
> Christopher Wright Wrote:
> 
>> On the other hand, what about subclasses? They can't override the 
>> behavior of an operator overload, if operator overloading uses static 
>> methods. You're reduced to writing your overloads as:
>>
>> class Foo
>> {
>> 	static Foo opAddAssign (Foo left, Foo right)
>> 	{
>> 		return left.addAssign(right);
>> 	}
>> }
>>
> 
> I don't understand your example. It was my understanding that static methods cannot be overridden. (there is no vtable entry for a static method)

That is my point. Static methods cannot be overridden. I want virtual 
operator overloads.

> Maybe you thought that I an requesting for D's implementation of operator overloads to ONLY use static methods?

So your suggestion is to convert:

{{{
MyClass instance1, instance2;
auto instance3 = instance1 + instance2;
}}}

to:
{{{
MyClass instance1, instance2;
MyClass instance3;
static if (isStaticMethod!(MyClass.opAdd))
	instance3 = MyClass.opAdd(instance1, instance2);
else
	instance3 = instance1.opAdd(instance2);
}}}

I don't see anything wrong with this suggestion. But I just don't see 
any compelling reason for it. I'm not getting off my chair to patch dmd 
to support this.
Top | Discussion index | About this forum | D home