Erik wrote:
Peter Doerfler wrote:
Why don't you use an anonymous union, like so?
This is exactly what I was looking for. It seems to work great. Many
thanks! Why did I not use it? I was just not smart enough. I tried to
use a union like
union T {
Coords c;
Uint32 i;
};
in the ordering functor, but I had to ditch that idea because it was not
allowed to have a type with constructor in a union. (And Coords has a
constructor, although it was omitted in the sample code here.)
struct Coords {
bool operator<(const Coords other) const;
union {
struct {
int x : 16, y : 16;
};
unsigned int z;
};
};
bool Coords::operator<(const Coords other) const {
return z < other.z;
}
I just double checked with -Wall -Wextra -pedantic and it says
error: ISO C++ prohibits anonymous structs
which seemingly doesn't mean that it doesn't work. Something similar is
in our production code. But the Standard is always right, so...
Here is a new version which has the advantage of hiding some
implementation details. You lose the bitfield initialization though.
I'm not sure whether the compiler is required to keep struct bar members
in a 32bit block now, I guess you need something like
__attribute__(packed), but I have no idea about those. On the other hand
the union should force this.
Maybe somebody can clarify although we're getting a bit off topic here.
Anyway this compiles without warnings under -Wall -Wextra -pedantic
-ansi and Comeau++ is also happy.
class foo {
public:
typedef unsigned short int16;
private:
struct bar {
int16 x;
int16 y;
};
union {
bar b;
unsigned int z;
};
public:
foo() : x(b.x), y(b.y) {}
foo(int16 xx, int16 yy) : x(b.x), y(b.y) {x=xx; y=yy;}
bool operator<(const foo& other) {return z<other.z;}
int16& x;
int16& y;
};
int main () {
foo f;
f.x = 1; f.y=0;
foo g(0,1);
return f<g;
}
Best, Peter