www.digitalmars.com         C & C++   DMDScript  

D - What's the Solution?

reply "anderson" <anderson firestar.com.au> writes:
Just to highlight a point, I would like to request how you would tackle a
problem like this in D.

Classes
    Vertex - Base class
    Line : Vertex
    Triangle : Line
    Polygon : Triangle
    ect...

What I would like to determine is how many Vertexes, lines, Triangles and
polygons are selected (individually). So for example

2 Vertexes are selected
5 lines are selected
6 Triangles are selected
3 Polygons are selected

So for example you may have these methords

//Although these could be done as an property
VertexObject.setSelected() //Sets this object to selected
VertexObject.getSelected() //Gets if this object is selected
LineObject.setSelected() //Sets this object to selected
ect..

VertexClass.getSelected() //gets the total amount of selected vertexes for
the vertex class
LineClass.getSelected() //gets the total amount of selected vertexes for the
line class
ect..

Easy right, heres a couple of important ground rules to make things more
difficult:
1. All code details must be contained within the class itself.
2. This code should only need to be written once in the BASE class.
Subsequent classes should inherit this property.
3. Needs to be resonably simple because the task is resonably simple.
Jul 18 2002
parent reply "Sean L. Palmer" <seanpalmer earthlink.net> writes:
Lines are not Vertices.  Polygons are not Triangles.

You should be using HasA, not IsA relationships.

So maybe they all derive from class GeometricPrimitive.

Hiding this all in the base class is hard;  what you'd have to do is have
each subclass register itself with the base class and have some kind of
virtual "GetType()" function to let the base class know what kind it is so
it can keep a tally.

Probably:

class GeometricPrimitive
{
private:
    static int[] countSelected; // how many of each type are selected
    bool selected; // if this is selected
protected:
    int getType() { assert(false); } // how do you make pure virtual
functions in D?
public:
    void setSelected()
    {
        selected = true;
        countSelected.length = max(countSelected.length, getType()+1); //
does D have builtin min/max/range/swap ?
        ++countSelected[getType()];
    }
    bool getSelected()
    {
        return selected;
    }
    int getTotalSelectedOfType()
    {
        return countSelected(getType());
    }
}

class Vertex : GeometricPrimitive
{
    int getType() { return 0; }
}

class Line : GeometricPrimitive
{
    int getType() { return 1; }
}

Something like that perhaps.

Sean

"anderson" <anderson firestar.com.au> wrote in message
news:ah82lm$16km$1 digitaldaemon.com...
 Just to highlight a point, I would like to request how you would tackle a
 problem like this in D.

 Classes
     Vertex - Base class
     Line : Vertex
     Triangle : Line
     Polygon : Triangle
     ect...

 What I would like to determine is how many Vertexes, lines, Triangles and
 polygons are selected (individually). So for example

 2 Vertexes are selected
 5 lines are selected
 6 Triangles are selected
 3 Polygons are selected

 So for example you may have these methords

 //Although these could be done as an property
 VertexObject.setSelected() //Sets this object to selected
 VertexObject.getSelected() //Gets if this object is selected
 LineObject.setSelected() //Sets this object to selected
 ect..

 VertexClass.getSelected() //gets the total amount of selected vertexes for
 the vertex class
 LineClass.getSelected() //gets the total amount of selected vertexes for

 line class
 ect..

 Easy right, heres a couple of important ground rules to make things more
 difficult:
 1. All code details must be contained within the class itself.
 2. This code should only need to be written once in the BASE class.
 Subsequent classes should inherit this property.
 3. Needs to be resonably simple because the task is resonably simple.

Jul 19 2002
next sibling parent reply "anderson" <anderson firestar.com.au> writes:
"Sean L. Palmer" <seanpalmer earthlink.net> wrote in message
news:ah8k4f$1oop$1 digitaldaemon.com...
 Lines are not Vertices.  Polygons are not Triangles.

Thanks for your reply, but it doesn't meet the requirements. Have you ever created a drawing package? Polygons are made of triangles, triangles of Vertices ect... I didn't mention that each vertex (line, triangle) is a group. Anyhow that's beside the point. I don't care what names are used, it's just for example purposes only (I'm not actually implementing this code) as long as its hyracical in nature.
 You should be using HasA, not IsA relationships.
 So maybe they all derive from class GeometricPrimitive.

 Hiding this all in the base class is hard;  what you'd have to do is have
 each subclass register itself with the base class and have some kind of
 virtual "GetType()" function to let the base class know what kind it is so
 it can keep a tally.

 Probably:

 class GeometricPrimitive
 {
 private:
     static int[] countSelected; // how many of each type are selected
     bool selected; // if this is selected
 protected:
     int getType() { assert(false); } // how do you make pure virtual
 functions in D?
 public:
     void setSelected()
     {
         selected = true;
         countSelected.length = max(countSelected.length, getType()+1); //
 does D have builtin min/max/range/swap ?
         ++countSelected[getType()];
     }
     bool getSelected()
     {
         return selected;
     }
     int getTotalSelectedOfType()
     {
         return countSelected(getType());
     }
 }

 class Vertex : GeometricPrimitive
 {
     int getType() { return 0; }
 }

 class Line : GeometricPrimitive
 {
     int getType() { return 1; }
 }

 Something like that perhaps.

This breaks rule 2. These rules are not for breaking. Code should only be written in the base class. Writing it in the other classes not only means extra work for other programmers, but extra documentation. How do you suppose numbers are issued in your suggestion. One project could have many users that may not even be in the same company. Even I've solved that problem (using pointers) using a simular technique. I've use code like this all the time, it's not the question. I have an idea how D could be improved to deal with these problems. I think that other will draw to that some conclusion, so I won't mention it now.
Jul 19 2002
parent reply "Sean L. Palmer" <seanpalmer earthlink.net> writes:
You didn't specify that NO code could be added to the derived classes.  Only
that the getSelected methods weren't to be implemented in the derived
classes.  ;)

I've run into that same problem before and the best solution is to use the
classinfo as the index somehow.  I just wasn't sure of D's classinfo syntax
and naming so I didn't put it into the example.

Sean

"anderson" <anderson firestar.com.au> wrote in message
news:ahaq8u$ub4$1 digitaldaemon.com...
 "Sean L. Palmer" <seanpalmer earthlink.net> wrote in message
 news:ah8k4f$1oop$1 digitaldaemon.com...
 Lines are not Vertices.  Polygons are not Triangles.

Thanks for your reply, but it doesn't meet the requirements. Have you ever created a drawing package? Polygons are made of triangles, triangles of Vertices ect... I didn't mention that each vertex (line, triangle) is a group. Anyhow that's beside the point. I don't care what names are used, it's just for example purposes only (I'm not actually implementing this code) as long as its hyracical in nature.
 You should be using HasA, not IsA relationships.
 So maybe they all derive from class GeometricPrimitive.

 Hiding this all in the base class is hard;  what you'd have to do is


 each subclass register itself with the base class and have some kind of
 virtual "GetType()" function to let the base class know what kind it is


 it can keep a tally.

 Probably:

 class GeometricPrimitive
 {
 private:
     static int[] countSelected; // how many of each type are selected
     bool selected; // if this is selected
 protected:
     int getType() { assert(false); } // how do you make pure virtual
 functions in D?
 public:
     void setSelected()
     {
         selected = true;
         countSelected.length = max(countSelected.length, getType()+1);


 does D have builtin min/max/range/swap ?
         ++countSelected[getType()];
     }
     bool getSelected()
     {
         return selected;
     }
     int getTotalSelectedOfType()
     {
         return countSelected(getType());
     }
 }

 class Vertex : GeometricPrimitive
 {
     int getType() { return 0; }
 }

 class Line : GeometricPrimitive
 {
     int getType() { return 1; }
 }

 Something like that perhaps.

This breaks rule 2. These rules are not for breaking. Code should only be written in the base class. Writing it in the other classes not only means extra work for other programmers, but extra documentation. How do you suppose numbers are issued in your suggestion. One project could have many users that may not even be in the same company. Even I've solved that problem (using pointers) using a simular technique. I've use code like

 all the time, it's not the question.  I have an idea how D could be

 to deal with these problems. I think that other will draw to that some
 conclusion, so I won't mention it now.

Jul 20 2002
parent reply "anderson" <anderson firestar.com.au> writes:
"Sean L. Palmer" <seanpalmer earthlink.net> wrote in message
news:ahckrq$77p$1 digitaldaemon.com...
 You didn't specify that NO code could be added to the derived classes.

 that the getSelected methods weren't to be implemented in the derived
 classes.  ;)

Well that's what I ment by 2. 2. This code should only should be written once in the BASE class. Subsequent classes should inherit this property.
 I've run into that same problem before and the best solution is to use the
 classinfo as the index somehow.  I just wasn't sure of D's classinfo

 and naming so I didn't put it into the example.

That still doesn't solve 2.
 Sean

Jul 20 2002
parent reply "Sean L. Palmer" <seanpalmer earthlink.net> writes:
"anderson" <anderson firestar.com.au> wrote in message
news:ahd447$lu1$1 digitaldaemon.com...
 "Sean L. Palmer" <seanpalmer earthlink.net> wrote in message
 news:ahckrq$77p$1 digitaldaemon.com...
 You didn't specify that NO code could be added to the derived classes.

 that the getSelected methods weren't to be implemented in the derived
 classes.  ;)

Well that's what I ment by 2. 2. This code should only should be written once in the BASE class. Subsequent classes should inherit this property.
 I've run into that same problem before and the best solution is to use


 classinfo as the index somehow.  I just wasn't sure of D's classinfo

 and naming so I didn't put it into the example.

That still doesn't solve 2.

Sure it does. Just replace getType() with int(&classinfo(*this)) or something similar. It would be nice if classinfo had some generated int identifier or perhaps enum? that could be used for this purpose. Haven't looked into it much. Sean
Jul 21 2002
parent reply Pavel Minayev <evilone omen.ru> writes:
On Sun=2C 21 Jul 2002 09=3A36=3A30 -0700 =22Sean L=2E Palmer=22
=3Cseanpalmer=40earthlink=2Enet=3E 
wrote=3A

=3E Sure it does=2E  Just replace getType=28=29 with
int=28&classinfo=28*this=29=29 or
=3E something similar=2E

Better yet=2C use an associative array=3A
=09
=09int=5BClassInfo=5D countSelected=3B

Then=2C no need for getType=28=29=2E Just use =2Eclassinfo of object=2E
Jul 21 2002
next sibling parent reply "anderson" <anderson firestar.com.au> writes:
What type of numbers does ClassInfo return? Will the algorithm need a hash
table?

"Pavel Minayev" <evilone omen.ru> wrote in message
news:CFN374589713982292 news.digitalmars.com...
On Sun, 21 Jul 2002 09:36:30 -0700 "Sean L. Palmer"
<seanpalmer earthlink.net>
wrote:

 Sure it does.  Just replace getType() with int(&classinfo(*this)) or
 something similar.

Better yet, use an associative array: int[ClassInfo] countSelected; Then, no need for getType(). Just use .classinfo of object.
Jul 22 2002
next sibling parent reply Russ Lewis <spamhole-2001-07-16 deming-os.org> writes:
anderson wrote:

 What type of numbers does ClassInfo return? Will the algorithm need a hash
 table?

D provides associative arrays built-in. You don't have to worry about the internals; Walter does that for you! -- The Villagers are Online! http://villagersonline.com .[ (the fox.(quick,brown)) jumped.over(the dog.lazy) ] .[ (a version.of(English).(precise.more)) is(possible) ] ?[ you want.to(help(develop(it))) ]
Jul 22 2002
parent "anderson" <anderson firestar.com.au> writes:
Oh, I get that. Thanks.

"Russ Lewis" <spamhole-2001-07-16 deming-os.org> wrote in message
news:3D3BF7FB.6C9C809A deming-os.org...
 anderson wrote:

 What type of numbers does ClassInfo return? Will the algorithm need a


 table?

D provides associative arrays built-in. You don't have to worry about the internals; Walter does that for you! -- The Villagers are Online! http://villagersonline.com .[ (the fox.(quick,brown)) jumped.over(the dog.lazy) ] .[ (a version.of(English).(precise.more)) is(possible) ] ?[ you want.to(help(develop(it))) ]

Jul 22 2002
prev sibling parent reply Pavel Minayev <evilone omen.ru> writes:
On Mon, 22 Jul 2002 18:04:08 +0800 "anderson" <anderson firestar.com.au> wrote:

 What type of numbers does ClassInfo return? Will the algorithm need a hash
 table?

classinfo property is not a number, it's a reference to ClassInfo object. But there's nothing wrong in using object references as hashtable keys. =)
Jul 22 2002
parent reply "Walter" <walter digitalmars.com> writes:
"Pavel Minayev" <evilone omen.ru> wrote in message
news:CFN374600443827431 news.digitalmars.com...
 On Mon, 22 Jul 2002 18:04:08 +0800 "anderson" <anderson firestar.com.au>

 What type of numbers does ClassInfo return? Will the algorithm need a


 table?

classinfo property is not a number, it's a reference to ClassInfo object. But there's nothing wrong in using object references as hashtable keys. =)

One of my intentions is that it becomes easy to see if two handles are the same type with: if (h1.classinfo === h2.classinfo)
Aug 01 2002
parent reply Pavel Minayev <evilone omen.ru> writes:
On Thu, 1 Aug 2002 02:54:15 -0700 "Walter" <walter digitalmars.com> wrote:

 One of my intentions is that it becomes easy to see if two handles are the
 same type with:
     if (h1.classinfo === h2.classinfo)

I wonder why you use ===, not == ? I mean, there is only one ClassInfo object per class, so comparing references should do.
Aug 01 2002
parent reply "Walter" <walter digitalmars.com> writes:
"Pavel Minayev" <evilone omen.ru> wrote in message
news:CFN374700122923032 news.digitalmars.com...
 On Thu, 1 Aug 2002 02:54:15 -0700 "Walter" <walter digitalmars.com> wrote:

 One of my intentions is that it becomes easy to see if two handles are


 same type with:
     if (h1.classinfo === h2.classinfo)

ClassInfo object per class, so comparing references should do.

=== does compare references!
Aug 03 2002
parent reply Pavel Minayev <evilone omen.ru> writes:
On Sat, 3 Aug 2002 11:37:11 -0700 "Walter" <walter digitalmars.com> wrote:

 same type with:
     if (h1.classinfo === h2.classinfo)

ClassInfo object per class, so comparing references should do.

=== does compare references!

Is it so both for arrays and objects? By the way, I've looked at default Object.cmp() - compares references as well. So it all doesn't really matter. =)
Aug 03 2002
parent "Walter" <walter digitalmars.com> writes:
"Pavel Minayev" <evilone omen.ru> wrote in message
news:CFN374721026579514 news.digitalmars.com...
 On Sat, 3 Aug 2002 11:37:11 -0700 "Walter" <walter digitalmars.com> wrote:

 same type with:
     if (h1.classinfo === h2.classinfo)

ClassInfo object per class, so comparing references should do.

=== does compare references!

Is it so both for arrays and objects?

Yes.
Aug 03 2002
prev sibling parent reply "anderson" <anderson firestar.com.au> writes:
"Pavel Minayev" <evilone omen.ru> wrote in message
news:CFN374589713982292 news.digitalmars.com...
On Sun, 21 Jul 2002 09:36:30 -0700 "Sean L. Palmer"
<seanpalmer earthlink.net>
wrote:

 Sure it does.  Just replace getType() with int(&classinfo(*this)) or
 something similar.

 Better yet, use an associative array:

 int[ClassInfo] countSelected;

 Then, no need for getType(). Just use .classinfo of object.

Which leads me to my point. So to call, " int getTotalSelectedOfType() { return countSelected(this.classinfo()); } " I'd have to be virutal and static right? Otherwise I'd have to have an existing object to call it. Also doesn't this denote the need for an object? I'd like to quarie the class.
Jul 22 2002
next sibling parent "anderson" <anderson firestar.com.au> writes:
"anderson" <anderson firestar.com.au> wrote in message
news:ahgls0$130b$1 digitaldaemon.com...
 "Pavel Minayev" <evilone omen.ru> wrote in message
 news:CFN374589713982292 news.digitalmars.com...
 On Sun, 21 Jul 2002 09:36:30 -0700 "Sean L. Palmer"
 <seanpalmer earthlink.net>
 wrote:

 Sure it does.  Just replace getType() with int(&classinfo(*this)) or
 something similar.

 Better yet, use an associative array:

 int[ClassInfo] countSelected;

 Then, no need for getType(). Just use .classinfo of object.

Which leads me to my point. So to call, " int getTotalSelectedOfType() {

     }
 "

 I'd have to be virutal and static right?

 Otherwise I'd have to have an existing object to call it. Also doesn't

 denote the need for an object? I'd like to quarie the class.

Jul 22 2002
prev sibling parent reply Pavel Minayev <evilone omen.ru> writes:
On Mon=2C 22 Jul 2002 18=3A19=3A01 +0800 =22anderson=22
=3Canderson=40firestar=2Ecom=2Eau=3E wrote=3A

=3E Which leads me to my point=2E
=3E 
=3E So to call=2C
=3E 
=3E =22
=3E     int getTotalSelectedOfType=28=29
=3E     {
=3E         return countSelected=28this=2Eclassinfo=28=29=29=3B
=3E     }
=3E =22
=3E 
=3E I'd have to be virutal and static right=3F
=3E 
=3E Otherwise I'd have to have an existing object to call it=2E Also doesn't
this
=3E denote the need for an object=3F I'd like to quarie the class=2E

You can=2E Just let it take a classinfo as an argument=3A

=09static int getTotalSelectedOfType=28ClassInfo ci=29
=09{
=09=09return countSelected=5Bci=5D=3B
=09}

And then=3A

=09getTotalSelectedOfType=28Vertex=2Eclassinfo=29=3B
Jul 22 2002
parent reply "anderson" <anderson firestar.com.au> writes:
Thanks. Cool, you could never do that in C++.

CountSelected becomes practicly a VT anyway. I still think think things
would have been simpler with virtual statics but this is close enough I
suppose.

//With virtual statics

class GeometricPrimitive
{
private:
    static virtual int countSelected;
    bool selected;
public:
    void setSelected()
    {
        selected = true;
        countSelected.length++;
    }
    bool isSelected()
    {
        return selected;
    }
    static virtual int getNumbSelected()
    {
        return countSelected;
    }
}

No need for arrays or anything, and it makes more sense.

 You can. Just let it take a classinfo as an argument:

 static int getTotalSelectedOfType(ClassInfo ci)
 {
 return countSelected[ci];
 }

 And then:

 getTotalSelectedOfType(Vertex.classinfo);

Jul 22 2002
next sibling parent "anderson" <anderson firestar.com.au> writes:
Whoops, forgot to remove the length++

"anderson" <anderson firestar.com.au> wrote in message
news:ahia9e$2p7u$1 digitaldaemon.com...
 Thanks. Cool, you could never do that in C++.

 CountSelected becomes practicly a VT anyway. I still think think things
 would have been simpler with virtual statics but this is close enough I
 suppose.

 //With virtual statics

 class GeometricPrimitive
 {
 private:
     static virtual int countSelected;
     bool selected;
 public:
     void setSelected()
     {
         selected = true;

     }
     bool isSelected()
     {
         return selected;
     }
     static virtual int getNumbSelected()
     {
         return countSelected;
     }
 }

 No need for arrays or anything, and it makes more sense.

 You can. Just let it take a classinfo as an argument:

 static int getTotalSelectedOfType(ClassInfo ci)
 {
 return countSelected[ci];
 }

 And then:

 getTotalSelectedOfType(Vertex.classinfo);


Jul 22 2002
prev sibling parent reply Pavel Minayev <evilone omen.ru> writes:
On Tue, 23 Jul 2002 09:13:43 +0800 "anderson" <anderson firestar.com.au> wrote:

 Thanks. Cool, you could never do that in C++.

Why? You can have map<type_info*, int>, and use typeid() operator.
Jul 23 2002
parent "anderson" <anderson firestar.com.au> writes:
"Pavel Minayev" <evilone omen.ru> wrote in message
news:CFN374606405046875 news.digitalmars.com...
 On Tue, 23 Jul 2002 09:13:43 +0800 "anderson" <anderson firestar.com.au>

 Thanks. Cool, you could never do that in C++.

Why? You can have map<type_info*, int>, and use typeid() operator.

I should have rephrased that to "how could you do that in C++". Thanks.
Jul 23 2002
prev sibling next sibling parent Pavel Minayev <evilone omen.ru> writes:
On Fri, 19 Jul 2002 02:02:49 -0700 "Sean L. Palmer" <seanpalmer earthlink.net> 
wrote:

     int getType() { assert(false); } // how do you make pure virtual
 functions in D?

abstract int getType();
Jul 21 2002
prev sibling parent "anderson" <anderson firestar.com.au> writes:
"Sean L. Palmer" <seanpalmer earthlink.net> wrote in message
news:ah8k4f$1oop$1 digitaldaemon.com...
 Lines are not Vertices.  Polygons are not Triangles.

 You should be using HasA, not IsA relationships.

Your right! I was thinking of anther project where we used a static machine for with 4 states/modes: Vertex, edge, polygon and object. The idea was that the same operations (translate, scale, rotate, ect...) could be applied to groups of objects in differn't modes. Yes, getNumbSelected was one of them and could be used to get the total amount of vertexes, edges, polygons and objects. If in vertex mode it would return the number of vertexes for a single object. If in object mode it would return 1 if the object was selected. But that's besides the point. isA (I perfer java style here) should be applied to boolean types.
Jul 22 2002