Last update March 3, 2008

Doc Comments /
Operator Overloading



Operator Overloading    

Table of contents of this page
Operator Overloading   
More Information   
FAQ   
Examples   
opCmp   
Messages   
comparison operators   
Links   

More Information    

FAQ    

Q: Why isn't opApply listed and where is it documented?

A: Probably not listed because it's not an 'operator' in the typical sense, as it doesn't replace an existing operator syntax, like '+' or '*'. It is documented with the ForeachStatement.

Q: How can I implement arraylike a[] = b[foo .. bar]?

A: Just overload the [ .. ] operator with opSlice and have it return an array.

Source: NG:digitalmars.D/12224

Q: From the page: "The member function opEquals() is defined as part of Object as: int opEquals(Object o);" Why would this return int rather than bool?

A: Supposedly for performance reasons.

Source: NG:digitalmars.D.bugs/7933, NG:digitalmars.D/43848

Note: The applicability of any performance reasons to opEquals is disputed - see NG:digitalmars.D/44064

Q: The documentation needs to mention opAssign (or the lack of it) and why it does not exist...

A: Look again. D does now have an opAssign, and it is documented.

Examples    

opCmp    

Implementing a custom opCmp for a struct to do lexicographical ordering: Note using ref parameters in opCmp is not good:
 *  http://d.puremagic.com/issues/show_bug.cgi?id=1861
 *  http://d.puremagic.com/issues/show_bug.cgi?id=1517

Version 1:
struct Pair
{
    int a, b;
    int opCmp(Pair rhs) {
        if (a!=rhs.a) return a<rhs.a?-1:1;
        if (b!=rhs.b) return b<rhs.b?-1:1;
        return 0;
    }
}
Version 2:
struct Pair
{
    int a, b;
    int opCmp(Pair rhs) {
        if (a!=rhs.a) return a-rhs.a;
        return b-rhs.b;
    }
}
Note this version suffers from potential overflow issues. The issue is that comparing values like int.max and -1 you get (int.max - (-1)) which doesn't fit into an int and "wraps around" to the other side. Instead of being a big positive number it becomes a negative number. If you're not concerned by that, though, it may be slightly faster than Version 1. If a and b were bytes or shorts, casting to int would be an acceptable approach, like return cast(int)a-cast(int)rhs.a.

Tests:

void main()
{
    assert( !(Pair(0,0)<Pair(0,0)) );
    assert( !(Pair(1,0)<Pair(0,0)) );
    assert( !(Pair(0,1)<Pair(0,0)) );
    assert( !(Pair(1,1)<Pair(0,0)) );
    assert(  (Pair(0,0)<Pair(1,0)) );
    assert( !(Pair(1,0)<Pair(1,0)) );
    assert(  (Pair(0,1)<Pair(1,0)) );
    assert( !(Pair(1,1)<Pair(1,0)) );

    assert(  (Pair(0,0)<Pair(0,1)) );
    assert( !(Pair(1,0)<Pair(0,1)) );
    assert( !(Pair(0,1)<Pair(0,1)) );
    assert( !(Pair(1,1)<Pair(0,1)) );
    assert(  (Pair(0,0)<Pair(1,1)) );
    assert(  (Pair(1,0)<Pair(1,1)) );
    assert(  (Pair(0,1)<Pair(1,1)) );
    assert( !(Pair(1,1)<Pair(1,1)) );
}

Messages    

1. opCmp version 2 -- is simply inaceptable form for opCmp

 int cmp(int a,int b) { return a-b; }    
Because of CmpIntegerOverflowProblem. And this form should be strongly avoided.

Left picture is values given by opCmp.v1 and right is values given by opCmp.v2. Sign shown by color: red-positive, blue-negative, aqua-zero line.

<!-- kov_serg: syntax of ProWiki? is very different from MediaWiki?. And I don understand how to create links to new topic and how to insert picture -->

2. using ref parameters in opCmp is not an evil. But existing bug with sort only points to inpropper algorithm used, the same hiddend bug was in Borland Pascal 7.0 example of qsort.pas. And it was widely reproduced (for example: http://www.qslnet.de/member/dg1xpz/programm/tp/qsort.html or http://www.thur.de/~voland/pub/Pascal/qsort.pas). The problem apears only with indirect sorting (with reference on data). So sort algorithm should be changed to correct one in the next version.

Here is D source code to check the problem: http://www.digitalmars.com/webnews/newsgroups.php?art_group=digitalmars.D&message_id=67039&attachment_id=1&o=file.html

comparison operators    

While D's comparison operators, with their implicit conversion to comparisons against 0 certainly seem easier to optimize and clearer than C++'s overloaded operators, there is one obscure advantage to C++'s implementation.

If your use of these operators isn't to compute a value immediately, but to build up a representation of the expression - ie return a parse tree of the expression rather than execute the expression - you can do that in C++. You can not do that in D, as far as I can tell.

Links    


FrontPage | News | TestPage | MessageBoard | Search | Contributors | Folders | Index | Help | Preferences | Edit

Edit text of this page (date of last change: March 3, 2008 19:25 (diff))