Topic: Embedded enum


Author: clamage@Eng.Sun.COM (Steve Clamage)
Date: 1996/07/14
Raw View
Eric Gindrup <gindrup@okway.okstate.edu> writes:

>On this thread: If you're willing to use namespaces, what do you
>need enums for?  In fact, most simple inheritence can be replaced
>with namespace manipulation.  If namespaces are sufficiently
>beefed up, they could replace enums, structs, classes, ...

I don't see how. Enums (and structs, classes, ...) define types.
Namespaces define scopes. The two things are independent concepts.
I also don't see how combining these independent concepts into one
(i.e., beefing up namespaces) would add clarity or utility to C++.
Sounds like a step backward to me.
--
Steve Clamage, stephen.clamage@eng.sun.com
---
[ comp.std.c++ is moderated.  To submit articles: Try just posting with your
                newsreader.  If that fails, use mailto:std-c++@ncar.ucar.edu
  comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
  Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
  Comments? mailto:std-c++-request@ncar.ucar.edu
]





Author: William Dicks <wd@isis.co.za>
Date: 1996/07/02
Raw View
What are the chances of getting the concept of embedded enums into the
C++ language. Imagine having an enum declared somewhere, where you cannot
change it yourself. You realize this enum only has a few of the values
you would like to use, but you need to add to this enum without declaring
it again. eg.

enum Color{WHITE, YELLOW, GREEN};
 now to add:
enum myColor{{Color}, BLUE, BROWN, BLACK};

--
William G Dicks (Systems Analyst - C++ & Theology Graduate) wd@isis.co.za
ISIS Information Systems
Gauteng
South Africa
---
[ comp.std.c++ is moderated.  To submit articles: Try just posting with your
                newsreader.  If that fails, use mailto:std-c++@ncar.ucar.edu
  comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
  Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
  Comments? mailto:std-c++-request@ncar.ucar.edu
]





Author: Alexandre Oliva <oliva@dcc.unicamp.br>
Date: 1996/07/03
Raw View
William Dicks <wd@isis.co.za> writes:

> enum Color{WHITE, YELLOW, GREEN};
>  now to add:
> enum myColor{{Color}, BLUE, BROWN, BLACK};

Why not

enum myColor : Color { BLUE, BROWN, BLACK };

IMHO, this is a very special case of inheritance...

--
Alexandre Oliva
oliva@dcc.unicamp.br
Universidade Estadual de Campinas, Sco Paulo, Brasil
---
[ comp.std.c++ is moderated.  To submit articles: Try just posting with your
                newsreader.  If that fails, use mailto:std-c++@ncar.ucar.edu
  comp.std.c++ FAQ: http://reality.sgi.com/austern/std-c++/faq.html
  Moderation policy: http://reality.sgi.com/austern/std-c++/policy.html
  Comments? mailto:std-c++-request@ncar.ucar.edu
]





Author: damian@molly.cs.monash.edu.au (Damian Conway)
Date: 1996/07/03
Raw View
William Dicks <wd@isis.co.za> writes:

>What are the chances of getting the concept of embedded enums into the
>C++ language. Imagine having an enum declared somewhere, where you cannot
>change it yourself. You realize this enum only has a few of the values
>you would like to use, but you need to add to this enum without declaring
>it again. eg.

>enum Color{WHITE, YELLOW, GREEN};
> now to add:
>enum myColor{{Color}, BLUE, BROWN, BLACK};

This is another incarnation of enum inheritance:

 // THIS IS NOT VALID C++ (AT LEAST IN THIS SPACETIME)
 enum myColour : public Color
 {
  BLUE = GREEN+1,
  BROWN,
  BLACK
 };

which, if memory serves, is periodically suggested and rejected.

Now that namespaces are available, there's probably already a way to do it:


 // WARNING, WILL ROBINSON, HIGHLY SPECULATIVE CODE APPROACHING!

 namespace Color
 {
  enum {WHITE, YELLOW, GREEN};
 }

 namespace myColour
 {
  enum
  {
   WHITE = Color::WHITE,
   YELLOW,
   GREEN,
   BLUE,
   BROWN,
   BLACK
  };
 }

 using namespace myColour;


damian
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  who: Damian Conway                 email: damian@cs.monash.edu.au
where: Computer Science Dept.          web: http://www.cs.monash.edu.au/~damian
       Monash University             phone: +61-3-9905-5184
       Clayton 3168                    fax: +61-3-9905-5146
       AUSTRALIA                     quote: "A pessimist is never disappointed."


[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: Eric Gindrup <gindrup@okway.okstate.edu>
Date: 1996/07/05
Raw View
Damian Conway wrote:
> William Dicks <wd@isis.co.za> writes:
>> What are the chances of getting the concept of embedded enums into
>> the C++ language. Imagine having an enum declared somewhere, where
>> you cannot change it yourself. You realize this enum only has a
>> few of the values you would like to use, but you need to add to
>> this enum without declaring it again. eg.
>
>>enum Color{WHITE, YELLOW, GREEN};
>> now to add:
>>enum myColor{{Color}, BLUE, BROWN, BLACK};[...]
> Now that namespaces are available, there's probably already a way
> to do it:[...]
>    namespace Color
>    {
>       enum {WHITE, YELLOW, GREEN};
>    }
>
>    namespace myColour
>    {
>       enum
>       {
>          WHITE = Color::WHITE,
>          YELLOW, GREEN, BLUE, BROWN, BLACK
>       };
>    }
>
>    using namespace myColour;
>
> damian[...]
>   who: Damian Conway                 email: damian@cs.monash.edu.au[...]

Style question: Do you *actually* put tabs in your code?

Related to a different thread: Should namespace declarations require
closing semicolons or not? :)

On this thread: If you're willing to use namespaces, what do you
need enums for?  In fact, most simple inheritence can be replaced
with namespace manipulation.  If namespaces are sufficiently
beefed up, they could replace enums, structs, classes, ...
  -- Eric Gindrup ! gindrup@okway.okstate.edu

The following example wouuld probably fail horribly under the
current standard.  You may also want to change every occurence
of ++color_count to color_count++.

namespace Color
{
   size_t color_count = 0;  //Uh-oh, my C-isms are sticking out...
   int    White  = ++color_count,
          Yellow = ++color_count,
          Green  = ++color_count;
}
namespace MyColour
{
   using namespace Color;
   int    Blue  = ++color_count,
          Brown = ++color_count,
          Black = ++color_count;
}
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: kuehl@uzwil.informatik.uni-konstanz.de (Dietmar Kuehl)
Date: 1996/07/06
Raw View
Hi,
Damian Conway (damian@molly.cs.monash.edu.au) wrote:
: This is another incarnation of enum inheritance:

:  // THIS IS NOT VALID C++ (AT LEAST IN THIS SPACETIME)
:  enum myColour : public Color
:  {
:   BLUE = GREEN+1,
:   BROWN,
:   BLACK
:  };

: which, if memory serves, is periodically suggested and rejected.

Note, that "enum inheritance" differes from normal inheritance in a
very central way: Normal inheritance creates a class more special while
enum inheritance generates an enum which is more general: While it is
normally possible to use an object (publically) of derived class
wherever an object of the base class can be used, this is not true for
enum inheritance. Consider e.g.  this code:

  enum foobar
  {
    foo = 0,
    bar = 1
  };

  void f(foobar const &fb)
  {
    switch (fb)
    {
      case foo: /*...*/; break;
      case bar: /*...*/; break;
    }
  }

This code handles all values which can possibly represented with a
'foobar'.  If enum inheritance would be allowed, this code might break
due to the fact that a reference to a derived enum which is not
represented by 'foo' or 'bar' is passed as argument. The same problem
does not exist with normal inheritance.
--
<mailto:dietmar.kuehl@uni-konstanz.de>
<http://www.informatik.uni-konstanz.de/~kuehl/>
I am a realistic optimist - that's why I appear to be slightly pessimistic


[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: damian@molly.cs.monash.edu.au (Damian Conway)
Date: 1996/07/08
Raw View
Eric Gindrup <gindrup@okway.okstate.edu> writes:

>Damian Conway wrote:
>> Now that namespaces are available, there's probably already a way
>> to do it:[...]
>>    namespace Color
>>    {
>>       enum {WHITE, YELLOW, GREEN};
>>    }
>>
>>    namespace myColour
>>    {
>>       enum
>>       {
>>          WHITE = Color::WHITE,
>>          YELLOW, GREEN, BLUE, BROWN, BLACK
>>       };
>>    }
>>
>>    using namespace myColour;

>Style question: Do you *actually* put tabs in your code?

Yes. But I don't waste them on internet followups ;-)

>Related to a different thread: Should namespace declarations require
>closing semicolons or not? :)

Yeah, that's one thing I really dislike about C++. :-)
I guess the way to think about namespaces is as being a partitioning
mechanism (like 'extern "C"'), rather than being a "declaration".

>On this thread: If you're willing to use namespaces, what do you
>need enums for?

Overloading?
Restriction of assignable values?


damian
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  who: Damian Conway               email: damian@cs.monash.edu.au
where: Computer Science Dept.        web: http://www.cs.monash.edu.au/~damian
       Monash University           phone: +61-3-9905-5184
       Clayton 3168                  fax: +61-3-9905-5146
       AUSTRALIA                   quote: "A pessimist is never disappointed."
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: damian@molly.cs.monash.edu.au (Damian Conway)
Date: 1996/07/08
Raw View
kuehl@uzwil.informatik.uni-konstanz.de (Dietmar Kuehl) writes:

>: This is another incarnation of enum inheritance:
>: which, if memory serves, is periodically suggested and rejected.

>Note, that "enum inheritance" differes from normal inheritance in a
>very central way: Normal inheritance creates a class more special while
>enum inheritance generates an enum which is more general: While it is
>normally possible to use an object (publically) of derived class
>wherever an object of the base class can be used, this is not true for
>enum inheritance. Consider e.g.  this code:

>  enum foobar
>  {
>    foo = 0,
>    bar = 1
>  };

>  void f(foobar const &fb)
>  {
>    switch (fb)
>    {
>      case foo: /*...*/; break;
>      case bar: /*...*/; break;
>    }
>  }

>This code handles all values which can possibly represented with a
>'foobar'.  If enum inheritance would be allowed, this code might break
>due to the fact that a reference to a derived enum which is not
>represented by 'foo' or 'bar' is passed as argument. The same problem
>does not exist with normal inheritance.

Just playing the Devil's Advocate here (>:-), but is this any worse than
the problem that already exists? Just to extend your example a little:

 enum foobar
 {
   foo = 0,
   bar = 1,
   baz = 2,
   bop = 4
 };

 void f (foobar const &fb)
 {
   switch (fb)
   {
     case foo: /*...*/; break;
     case bar: /*...*/; break;
     case baz: /*...*/; break;
     case bop: /*...*/; break;
   }
 }

Suppose someone calls f(foo|baz|bop)???

This possibility means that most (if not all) such functions either need to
deal with each bit separately or need a default case to swallow such
composite values.

Either of the above solutions handles an enum derived from foobar just as
effectively. It just means that if you're going to pass a foobar by
reference, in the presence of enum inheritance you have to be a little more
careful.

BTW: Presumably if a value from an enum derived from foobar is passed by
     _copy_ (as one would normally do under most circumstances), that value
     would sliced back to the requisite number of bits for a foobar and
     there would be no problem.

damian
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
  who: Damian Conway                 email: damian@cs.monash.edu.au
where: Computer Science Dept.          web: http://www.cs.monash.edu.au/~damian
       Monash University             phone: +61-3-9905-5184
       Clayton 3168                    fax: +61-3-9905-5146
       AUSTRALIA                     quote: "A pessimist is never disappointed."


[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: smeyers@teleport.com (Scott Meyers)
Date: 1996/07/10
Raw View
In article <damian.836779782@molly.cs.monash.edu.au>,
Damian Conway <damian@molly.cs.monash.edu.au> wrote:
| Just playing the Devil's Advocate here (>:-), but is this any worse than
| the problem that already exists? Just to extend your example a little:
|
|  enum foobar
|  {
|    foo = 0,
|    bar = 1,
|    baz = 2,
|    bop = 4
|  };
|
|  void f (foobar const &fb)
|  {
|    switch (fb)
|    {
|      case foo: /*...*/; break;
|      case bar: /*...*/; break;
|      case baz: /*...*/; break;
|      case bop: /*...*/; break;
|    }
|  }
|
| Suppose someone calls f(foo|baz|bop)???

I don't think such a call should compile.  The type of foo|baz|bop is int,
and there's no implicit conversion from int to foobar.  You'd have to use a
cast.

Scott
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: seurer@rchland.ibm.com (Bill Seurer)
Date: 1996/07/10
Raw View
In article <damian.836352675@molly.cs.monash.edu.au>,
damian@molly.cs.monash.edu.au (Damian Conway) writes:
|>
|> Now that namespaces are available, there's probably already a way to do it:
|>
|>
|>  // WARNING, WILL ROBINSON, HIGHLY SPECULATIVE CODE APPROACHING!
|>
|>  namespace Color
|>  {
|>   enum {WHITE, YELLOW, GREEN};
|>  }
|>
|>  namespace myColour
|>  {
|>   enum
|>   {
|>    WHITE = Color::WHITE,
|>    YELLOW,
|>    GREEN,
|>    BLUE,
|>    BROWN,
|>    BLACK
|>   };
|>  }
|>
|>  using namespace myColour;

That won't quite do it because the enums aren't interchangable (in the
inheritance sense) as types.  Enums are types in C++ after all and not
just lists of named constants.
--

- Bill Seurer     ID Tools and Compiler Development      IBM Rochester, MN
  Business: BillSeurer@vnet.ibm.com               Home: BillSeurer@aol.com
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]





Author: damian@molly.cs.monash.edu.au (Damian Conway)
Date: 1996/07/12
Raw View
smeyers@teleport.com (Scott Meyers) writes:

>| Suppose someone calls f(foo|baz|bop)???

>I don't think such a call should compile.  The type of foo|baz|bop is int,
>and there's no implicit conversion from int to foobar.  You'd have to use a
>cast.

Okay, I fumbled the call syntax, but that doesn't materially affect my
original counterargument. Since a const foobar& is already able to be
being bound to a bitset which is not an explicitly declared foobar value,
it's no more dangerous to bind it to a value of a derived enum, as any code
using the const foobar& must allow for the possibility of an "unknown"
value anyway.

Which raises the question of whether an "explicit" enum declaration syntax
would be of value. I.e. something along the lines of:

 explicit enum DoorStatus {open, closed, unknown};
 DoorStatus ds = unknown;

 ds = open;     // OKAY
 ds = closed;      // OKAY

 ds = DoorStatus(open|closed); // COMPILER ERROR
     // (NOT AN EXPLICIT DoorStatus VALUE)

damian
---
[ comp.std.c++ is moderated.  To submit articles: try just posting with      ]
[ your news-reader.  If that fails, use mailto:std-c++@ncar.ucar.edu         ]
[ FAQ:      http://reality.sgi.com/employees/austern_mti/std-c++/faq.html    ]
[ Policy:   http://reality.sgi.com/employees/austern_mti/std-c++/policy.html ]
[ Comments? mailto:std-c++-request@ncar.ucar.edu                             ]