
Hi, I have written a bit of code to handle geometric vectors in a generic way, abstracting their dimension. The idea behind this code is to be able to apply one operation between two vectors, or a vector and a scalar, whatever their dimension, and writing it in an expandable way without having to modify any manipulation functions if a new geometric vector class is created. The other advantage is that the resulting assembly code is just as fast as if the functions had all been explicitly written. Right now I have three simple vector classes - ranging from vector2d to vector4d - that are not templetized since I like the idea of being able to access coordinates directly by their name vector3d vec; vec.x += 10.0f; to give you an example of the syntax, here is how you would add two vectors of different dimensions : vector2d v1(1.0f, 2.0f); vector3d v2(-1.0f, 3.0f, 2.0f); vector4d res; vector_add(v1, v2, res); /* res now contains (0.0f, 5.0f, 2.0f, 1.0f) */ the result is determined by the dimension of the third vector passed to vector_add. v1 is auto-promoted to act like a vector3d. v2 does not change. res gets (v1.x + v2.x, v1.y + v2.y, v1.z + v2.z, default_w_value). I didn't seem to find any information on a lib currently under development that provides geometric vector manipulation in that way - maybe apart from uBLAS - so I thought I would share this if anyone seems to be interested. BR, Olivier.

On Wed, Sep 20, 2006 at 05:25:39PM +0100, Olivier Grant wrote:
Hi,
I have written a bit of code to handle geometric vectors in a generic way, abstracting their dimension. The idea behind this code is to be able to apply one operation between two vectors, or a vector and a scalar, whatever their dimension, and writing it in an expandable way without having to modify any manipulation functions if a new geometric vector class is created. The other advantage is that the resulting assembly code is just as fast as if the functions had all been explicitly written.
Right now I have three simple vector classes - ranging from vector2d to vector4d - that are not templetized since I like the idea of being able to access coordinates directly by their name
<snip>
You can use template specialization to let you access coordinates directly by name. I.e., vector<1,float> has .x, vector<3,float> has .x/y/z, etc. Geoffrey

Hi, I agree, but between writing this : class vector3d { public: typedef float coordinate_type; typedef integral_constant<unsigned int, 3> dimension; vector3d( coordinate_type _x, coordinate_type _y, coordinate_type _z ) : x(_x), y(_y), z(_z) { } coordinate_type x, y, z; }; and this : template< typename coordinate_type, unsigned int dimension > class vector; template< > class vector<float, 3> { public: vector( float _x, float _y, float _z ) : x(_x), y(_y), z(_z) { } float x, y, z; }; I can't really see the difference apart from the syntax. both ways you can determine the number of coordinates and their type, which is whay is necessary to be able to write generic code that can manipulate vectors whatever their coordinate. I think the interesting part of my code is the implementation that does this abstraction, not the class implementation. BR, O. On 9/20/06, Geoffrey Irving <irving@cs.stanford.edu> wrote:
On Wed, Sep 20, 2006 at 05:25:39PM +0100, Olivier Grant wrote:
Hi,
I have written a bit of code to handle geometric vectors in a generic way, abstracting their dimension. The idea behind this code is to be able to apply one operation between two vectors, or a vector and a scalar, whatever their dimension, and writing it in an expandable way without having to modify any manipulation functions if a new geometric vector class is created. The other advantage is that the resulting assembly code is just as fast as if the functions had all been explicitly written.
Right now I have three simple vector classes - ranging from vector2d to vector4d - that are not templetized since I like the idea of being able to access coordinates directly by their name
<snip>
You can use template specialization to let you access coordinates directly by name. I.e., vector<1,float> has .x, vector<3,float> has .x/y/z, etc.
Geoffrey _______________________________________________ Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost

On Wed, Sep 20, 2006 at 05:48:55PM +0100, Olivier Grant wrote:
Hi,
I agree, but between writing this :
class vector3d { public: typedef float coordinate_type; typedef integral_constant<unsigned int, 3> dimension;
vector3d( coordinate_type _x, coordinate_type _y, coordinate_type _z ) : x(_x), y(_y), z(_z) { }
coordinate_type x, y, z; };
and this :
template< typename coordinate_type, unsigned int dimension > class vector;
template< > class vector<float, 3> { public: vector( float _x, float _y, float _z ) : x(_x), y(_y), z(_z) { }
float x, y, z; };
I can't really see the difference apart from the syntax. both ways you can determine the number of coordinates and their type, which is whay is necessary to be able to write generic code that can manipulate vectors whatever their coordinate. I think the interesting part of my code is the implementation that does this abstraction, not the class implementation.
The difference is that if you have an int and a T lying around, vector<i,T> lets you convert it into a vector type easily, and vectoriT does not. As you say, the only possible advantages to vectoriT are syntactic, so you might as well use the more flexible scheme. Geoffrey

On Wed, 2006-09-20 at 17:48 +0100, Olivier Grant wrote:
Right now I have three simple vector classes - ranging from vector2d to vector4d - that are not templetized since I like the idea of being able to access coordinates directly by their name
Unfortunately, this is not the best choice. As sson as you will have to iterate through the coordinates, you will find that having an array is necessary (at least if you do not want to have an awful efficiency....). Theo.

I agree on your point, on the other hand, you can do this : class vector3d { public: float x, y, z; float operator[]( int index ) const { return ((float *)this)[index]; } float & operator[]( int index ) { return ((float *)this)[index]; } /* ... */ }; in which case "v.x" and "v[0]" are the same thing. this is what I currently have. Now some people will argument its a hack maybe. Olivier. On 9/21/06, Theodore Papadopoulo <Theodore.Papadopoulo@sophia.inria.fr> wrote:
On Wed, 2006-09-20 at 17:48 +0100, Olivier Grant wrote:
Right now I have three simple vector classes - ranging from vector2d to vector4d - that are not templetized since I like the idea of being able to access coordinates directly by their name
Unfortunately, this is not the best choice. As sson as you will have to iterate through the coordinates, you will find that having an array is necessary (at least if you do not want to have an awful efficiency....).
Theo.
_______________________________________________ Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost

ok, what about this ? class vector3d_test { public: float x, y, z; float operator[]( int index ) const { return array[index]; } float & operator[]( int index ) { return array[index]; } union { struct { float x; float y; float z; } coord; float array[3]; }; }; but it means you have to call v.coord.x and v[0]. Olivier. On 9/21/06, me22 <me22.ca@gmail.com> wrote:
On 9/21/06, Olivier Grant <olivier.grant@gmail.com> wrote:
in which case "v.x" and "v[0]" are the same thing. this is what I currently have. Now some people will argument its a hack maybe.
Sure looks like illegal type punning to me... _______________________________________________ Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost

On 9/21/06, Olivier Grant <olivier.grant@gmail.com> wrote:
ok, what about this ?
class vector3d_test { public: float x, y, z;
float operator[]( int index ) const { return array[index]; }
float & operator[]( int index ) { return array[index]; }
union { struct { float x; float y; float z; } coord; float array[3]; }; };
but it means you have to call v.coord.x and v[0].
You can get around this using something like this: template< typename T > struct Vector4 { typedef size_t size_type; private: typedef T Vector4<T>::* const vec[4]; static const vec v; public: T x, y, z, w; Vector4(T _x = 0, T _y = 0, T _z = 0, T _w = 0): x(_x), y(_y), z(_z), w(_w) {} const T& operator[](size_type i) const { return this->*v[i]; } T& operator[](size_type i) { return this->*v[i]; } }; template< typename T > const typename Vector4<T>::vec Vector4<T>::v = { &Vector4<T>::x, &Vector4<T>::y, &Vector4<T>::z, &Vector4<T>::z }; Here's the original discussion from gamedev.net http://www.gamedev.net/community/forums/topic.asp?topic_id=261920 This wasn't written by me, I just remembered it from there and thought it might be interesting to you. --Mike

On Thu, 2006-09-21 at 08:54 -0400, Michael Fawcett wrote:
You can get around this using something like this:
template< typename T > struct Vector4 {
typedef size_t size_type;
private:
typedef T Vector4<T>::* const vec[4];
static const vec v;
public:
T x, y, z, w;
Vector4(T _x = 0, T _y = 0, T _z = 0, T _w = 0): x(_x), y(_y), z(_z), w(_w) {}
const T& operator[](size_type i) const { return this->*v[i]; }
T& operator[](size_type i) { return this->*v[i]; }
};
template< typename T > const typename Vector4<T>::vec Vector4<T>::v = { &Vector4<T>::x, &Vector4<T>::y, &Vector4<T>::z, &Vector4<T>::z };
Here's the original discussion from gamedev.net http://www.gamedev.net/community/forums/topic.asp?topic_id=261920
This wasn't written by me, I just remembered it from there and thought it might be interesting to you.
Interesting ! But I would certainly prefer the straightforward array implementation and an enum {X,Y,Z,Z} that allows the notation V[X] or V(X) (depending on your preference). The only fear I may have with your proposal is that by having complicated accesses, the compiler might not be able to do some optimizations. Theo.

On Thu, Sep 21, 2006 at 06:18:10PM +0200, Theodore Papadopoulo wrote:
On Thu, 2006-09-21 at 08:54 -0400, Michael Fawcett wrote:
You can get around this using something like this:
template< typename T > struct Vector4 {
typedef size_t size_type;
private:
typedef T Vector4<T>::* const vec[4];
static const vec v;
public:
T x, y, z, w;
Vector4(T _x = 0, T _y = 0, T _z = 0, T _w = 0): x(_x), y(_y), z(_z), w(_w) {}
const T& operator[](size_type i) const { return this->*v[i]; }
T& operator[](size_type i) { return this->*v[i]; }
};
template< typename T > const typename Vector4<T>::vec Vector4<T>::v = { &Vector4<T>::x, &Vector4<T>::y, &Vector4<T>::z, &Vector4<T>::z };
Here's the original discussion from gamedev.net http://www.gamedev.net/community/forums/topic.asp?topic_id=261920
This wasn't written by me, I just remembered it from there and thought it might be interesting to you.
This code is much too hard for the compiler to optimize. In order to handle a loop like for(int i=0;i<n;i++) f(V[i]); where n at runtime could be either 2 or 3, the compiler would have to independently determine the identity vec[i+1] = vec[i]+1. There's no way that would happen on any compiler now or in the immediate future.
Interesting ! But I would certainly prefer the straightforward array implementation and an enum {X,Y,Z,Z} that allows the notation
V[X] or V(X) (depending on your preference). The only fear I may have with your proposal is that by having complicated accesses, the compiler might not be able to do some optimizations.
This scheme means you can't have a vector called X, which happens to be one of the most commonly used vector names in my code (X for position, V for velocity). I don't think there's any reason to overthink this. The simple scheme works: template<class T> class vector3 { public: T x,y,z; vector3() { assert(&z == &x+3); } T& operator[](unsigned i) {assert(i<3);return (&x)[i];} }; It can probably even be considered standard compliant: if the assert doesn't hit, I'm pretty sure the standard guarantees that the code is correct. If I run the following code through gcc 4.0.1 vector3<float> X; X.y=3; X[2]=4; // critical line std::cout<<X.x; the compiler unpacks X into fields and complains about X$x being used uninitialized iff I comment out the critical line, so there shouldn't be any penalty to the existence of operator[] unless you use it in on a given vector. As a side note, is it possible to write that with a STATIC_ASSERT? Geoffrey

On 9/21/06, Theodore Papadopoulo <Theodore.Papadopoulo@sophia.inria.fr> wrote:
On Thu, 2006-09-21 at 08:54 -0400, Michael Fawcett wrote:
You can get around this using something like this:
<snip code>
Here's the original discussion from gamedev.net http://www.gamedev.net/community/forums/topic.asp?topic_id=261920
This wasn't written by me, I just remembered it from there and thought it might be interesting to you.
Interesting ! But I would certainly prefer the straightforward array implementation and an enum {X,Y,Z,Z} that allows the notation
V[X] or V(X) (depending on your preference). The only fear I may have with your proposal is that by having complicated accesses, the compiler might not be able to do some optimizations.
Theo.
There was another thread where the participants looked at the generated assembly (MSVS 7.1) and found that it was the same as indexing into an array. The really interesting thing was that the first time they forgot the const keyword and the generated code was sub-optimal. After fixing the const-correctness issues the VS 7.1 optimizer was able to produce code identical to array indexing. http://www.gamedev.net/community/forums/topic.asp?topic_id=230443&PageSize=25&WhichPage=2 No one has posted a detailed analysis of the generated code in more complex cases though, but for the simple case it appears that at least VS 7.1 can optimize the code just fine. --Mike

On Thu, Sep 21, 2006 at 02:17:30PM -0400, Michael Fawcett wrote:
On 9/21/06, Theodore Papadopoulo <Theodore.Papadopoulo@sophia.inria.fr> wrote:
On Thu, 2006-09-21 at 08:54 -0400, Michael Fawcett wrote:
You can get around this using something like this:
<snip code>
There was another thread where the participants looked at the generated assembly (MSVS 7.1) and found that it was the same as indexing into an array. The really interesting thing was that the first time they forgot the const keyword and the generated code was sub-optimal. After fixing the const-correctness issues the VS 7.1 optimizer was able to produce code identical to array indexing.
http://www.gamedev.net/community/forums/topic.asp?topic_id=230443&PageSize=25&WhichPage=2
No one has posted a detailed analysis of the generated code in more complex cases though, but for the simple case it appears that at least VS 7.1 can optimize the code just fine.
It's hard to be certain since they didn't actually show the code they were compiling, but judging by their pseudocode that test is entirely insufficient. If i is a compile time constant, v[i] is easy to optimize. The hard case is if i is a arbitrary runtime integer, as mentioned in my previous email. Geoffrey

On 9/21/06, Geoffrey Irving <irving@cs.stanford.edu> wrote:
It's hard to be certain since they didn't actually show the code they were compiling, but judging by their pseudocode that test is entirely insufficient. If i is a compile time constant, v[i] is easy to optimize. The hard case is if i is a arbitrary runtime integer, as mentioned in my previous email.
Absolutely, it's entirely out of the question if i is not a compile-time constant. --Mike

On Thu, Sep 21, 2006 at 03:08:15PM -0400, Michael Fawcett wrote:
On 9/21/06, Geoffrey Irving <irving@cs.stanford.edu> wrote:
It's hard to be certain since they didn't actually show the code they were compiling, but judging by their pseudocode that test is entirely insufficient. If i is a compile time constant, v[i] is easy to optimize. The hard case is if i is a arbitrary runtime integer, as mentioned in my previous email.
Absolutely, it's entirely out of the question if i is not a compile-time constant.
The code I posted trivially reduces to array lookup for any i, so it's certainly not "out of the question" based on the desired interface. Geoffrey

On 9/21/06, Geoffrey Irving <irving@cs.stanford.edu> wrote:
On Thu, Sep 21, 2006 at 03:08:15PM -0400, Michael Fawcett wrote:
On 9/21/06, Geoffrey Irving <irving@cs.stanford.edu> wrote:
It's hard to be certain since they didn't actually show the code they were compiling, but judging by their pseudocode that test is entirely insufficient. If i is a compile time constant, v[i] is easy to optimize. The hard case is if i is a arbitrary runtime integer, as mentioned in my previous email.
Absolutely, it's entirely out of the question if i is not a compile-time constant.
The code I posted trivially reduces to array lookup for any i, so it's certainly not "out of the question" based on the desired interface.
Sorry, I was referring to the code I posted, not yours. --Mike

Olivier Grant wrote:
I agree on your point, on the other hand, you can do this :
class vector3d { public: float x, y, z;
float operator[]( int index ) const { return ((float *)this)[index]; }
float & operator[]( int index ) { return ((float *)this)[index]; }
/* ... */ };
in which case "v.x" and "v[0]" are the same thing. this is what I currently have. Now some people will argument its a hack maybe.
I've sometimes done just: class vector3d { public: float x, y, z; float operator[]( int index ) const { return (&x)[index]; } /* ... */ }; /Marcus

Won't that not work in the presence of padding? Sorry for the TP, lookout webmail. -----Original Message----- From: boost-bounces@lists.boost.org on behalf of Marcus Lindblom Sent: Fri 9/22/2006 12:17 AM To: boost@lists.boost.org Subject: Re: [boost] Geometry/Vector Lib Olivier Grant wrote:
I agree on your point, on the other hand, you can do this :
class vector3d { public: float x, y, z;
float operator[]( int index ) const { return ((float *)this)[index]; }
float & operator[]( int index ) { return ((float *)this)[index]; }
/* ... */ };
in which case "v.x" and "v[0]" are the same thing. this is what I currently have. Now some people will argument its a hack maybe.
I've sometimes done just: class vector3d { public: float x, y, z; float operator[]( int index ) const { return (&x)[index]; } /* ... */ }; /Marcus

----Original Message---- From: Sohail Somani
Marcus Lindblom wrote:
Olivier Grant wrote:
I agree on your point, on the other hand, you can do this :
class vector3d { public: float x, y, z;
float operator[]( int index ) const { return ((float *)this)[index]; }
float & operator[]( int index ) { return ((float *)this)[index]; }
/* ... */ };
in which case "v.x" and "v[0]" are the same thing. this is what I currently have. Now some people will argument its a hack maybe.
I've sometimes done just:
class vector3d { public: float x, y, z;
float operator[]( int index ) const { return (&x)[index]; }
/* ... */ };
Won't that not work in the presence of padding?
In theory, yes. In practice, I can't see why any compiler would bother adding such padding. A more serious problem is if you start mixing usages. A compiler is quite likely to assume that assignments through the result of the index operator don't affect .y or .z, and optimize on that basis.
Sorry for the TP, lookout webmail. Reformatted :-)
-- Martin Bonner Martin.Bonner@Pitechnology.com Pi Technology, Milton Hall, Ely Road, Milton, Cambridge, CB4 6WZ, ENGLAND Tel: +44 (0)1223 203894

Martin Bonner wrote:
----Original Message---- From: Sohail Somani
Marcus Lindblom wrote:
Olivier Grant wrote:
I agree on your point, on the other hand, you can do this :
class vector3d { public: float x, y, z;
float operator[]( int index ) const { return ((float *)this)[index]; }
float & operator[]( int index ) { return ((float *)this)[index]; }
/* ... */ };
in which case "v.x" and "v[0]" are the same thing. this is what I currently have. Now some people will argument its a hack maybe.
I've sometimes done just:
class vector3d { public: float x, y, z;
float operator[]( int index ) const { return (&x)[index]; }
/* ... */ }; Won't that not work in the presence of padding? In theory, yes. In practice, I can't see why any compiler would bother adding such padding.
A more serious problem is if you start mixing usages. A compiler is quite likely to assume that assignments through the result of the index operator don't affect .y or .z, and optimize on that basis.
Why should it? The offset to memory will be the same, so it should treat it as access to the same memory location, if it optimizes well in the backend ('assembly' AST). Cheers, /Marcus

Hi! Martin Bonner schrieb:
Won't that not work in the presence of padding? In theory, yes. In practice, I can't see why any compiler would bother adding such padding.
A more serious problem is if you start mixing usages. A compiler is quite likely to assume that assignments through the result of the index operator don't affect .y or .z, and optimize on that basis.
This is not a more serious problem in my opinion. The most serious problem here is, that we are leaving the standard. It is open how the compiler does the class layout and it is definitifely illegal to access the class storage by converting "this" to an array of members. Apart from padding the compiler may do other things which will for sure mess up the array access (like reverse order of members, injecting additional information into the class, "this" pointing to the end of storage instead of the beginning, "this" being offset by a constant value, or whatever). I'd appreciate if we could all have the discipline to follow the standard. I'd like boost to continue being a portable C++ library. And I guess libraries relying on such "hacks" will have a hard time being accepted for boost. Frank

For accessing members of a vector, I've found I prefer using an index to access elements, with some special indicees predefined. This sidesteps the problem of needing to directly access a member in order to refer to a component by name. For instance: vector<int, 2> vec; vec[0] = 42; vec[_x] = 42; // does the same thing

Hi! Jason Hise schrieb:
vec[0] = 42; vec[_x] = 42; // does the same thing
"_x" is not allowed as a variable name. So we would need something else. And you don't want it to interfere with user code either. I can't estimate how many people would use a variable named "x" in a mathematical context. Frank

----Original Message---- From: boost-bounces@lists.boost.org [mailto:boost-bounces@lists.boost.org] On Behalf Of Frank Birbacher Sent: 05 October 2006 10:00 To: boost@lists.boost.org Subject: Re: [boost] Geometry/Vector Lib > Hi! > > Jason Hise schrieb: >> vec[0] = 42; >> vec[_x] = 42; // does the same thing > > "_x" is not allowed as a variable name. Yes it is. 17.4.3.1.2 [lib.global.names] in the standard says: - Each name that contains a double underscore (_ _) or begins with an underscore followed by an uppercase letter (2.11) is reserved to the implementation for any use. - Each name that begins with an underscore is reserved to the implementation for use as a name in the global namespace. _x is legal if it is defined in (eg) boost::geometry and brought in via a using statement. The real problem is that leading _ is a fairly common convention for "member variable", and as you mention below, a member named 'x' in a mathematical context is not inconceivable! -- Martin Bonner Martin.Bonner@Pitechnology.com Pi Technology, Milton Hall, Ely Road, Milton, Cambridge, CB4 6WZ, ENGLAND Tel: +44 (0)1223 203894

Jason Hise wrote:
For accessing members of a vector, I've found I prefer using an index to access elements, with some special indicees predefined. This sidesteps the problem of needing to directly access a member in order to refer to a component by name. For instance:
vector<int, 2> vec;
vec[0] = 42; vec[_x] = 42; // does the same thing
So, we need to support three different styles of access, at least, to make everyone happy? - vec[0] - vec.x - vec[_x] Cheers, /Marcus

"Marcus Lindblom" <macke@yar.nu> wrote in message news:45252C77.3050708@yar.nu...
Jason Hise wrote:
For accessing members of a vector, I've found I prefer using an index to access elements, with some special indicees predefined. This sidesteps the problem of needing to directly access a member in order to refer to a component by name. For instance:
vector<int, 2> vec;
vec[0] = 42; vec[_x] = 42; // does the same thing
So, we need to support three different styles of access, at least, to make everyone happy?
- vec[0] - vec.x - vec[_x]
Why not : at_x(vec) This allows all the above: T vec[3]; // array boost array and at_c<0>(vec) // Fusion style http://tinyurl.com/ftare and Views: http://spirit.sourceforge.net/dl_more/fusion_v2/libs/fusion/doc/html/fusion/... regards Andy Little

Frank Birbacher wrote:
Hi!
Martin Bonner schrieb:
Won't that not work in the presence of padding?
In theory, yes. In practice, I can't see why any compiler would bother adding such padding.
A more serious problem is if you start mixing usages. A compiler is quite likely to assume that assignments through the result of the index operator don't affect .y or .z, and optimize on that basis.
This is not a more serious problem in my opinion. The most serious problem here is, that we are leaving the standard. It is open how the compiler does the class layout and it is definitifely illegal to access the class storage by converting "this" to an array of members. Apart from padding the compiler may do other things which will for sure mess up the array access (like reverse order of members, injecting additional information into the class, "this" pointing to the end of storage instead of the beginning, "this" being offset by a constant value, or whatever).
How does the standard say on the suggestion of using &x instead of this? Would that be allowed?
I'd appreciate if we could all have the discipline to follow the standard. I'd like boost to continue being a portable C++ library. And I guess libraries relying on such "hacks" will have a hard time being accepted for boost.
Agreed. Cheers, /Marcus

Well due to the fact that floats are represented on 4 bytes, there shouldn't be any padding involved. Padding normally occures when certain member variables of a structure require certain alignment constraints or just for efficiency, but this shouldn't occur with a vector class (at least that is my understanding). It is the same thing with alignment. the beginning of the structure is placed on a certain boundary but doesn't affect the padding of elements within the structure. You could set this vector class to be 16 bytes aligned if you wanted to use them with SSE instructions, and you can still access the member with the array operator without problems. Olivier. On 9/22/06, Sohail Somani <s.somani@fincad.com> wrote:
Won't that not work in the presence of padding? Sorry for the TP, lookout webmail.
-----Original Message----- From: boost-bounces@lists.boost.org on behalf of Marcus Lindblom Sent: Fri 9/22/2006 12:17 AM To: boost@lists.boost.org Subject: Re: [boost] Geometry/Vector Lib
Olivier Grant wrote:
I agree on your point, on the other hand, you can do this :
class vector3d { public: float x, y, z;
float operator[]( int index ) const { return ((float *)this)[index]; }
float & operator[]( int index ) { return ((float *)this)[index]; }
/* ... */ };
in which case "v.x" and "v[0]" are the same thing. this is what I currently have. Now some people will argument its a hack maybe.
I've sometimes done just:
class vector3d { public: float x, y, z;
float operator[]( int index ) const { return (&x)[index]; }
/* ... */ };
/Marcus _______________________________________________ Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost

Olivier Grant wrote:
Well due to the fact that floats are represented on 4 bytes, there shouldn't be any padding involved. Padding normally occures when certain member variables of a structure require certain alignment constraints or just for efficiency, but this shouldn't occur with a vector class (at least that is my understanding).
It is the same thing with alignment. the beginning of the structure is placed on a certain boundary but doesn't affect the padding of elements within the structure. You could set this vector class to be 16 bytes aligned if you wanted to use them with SSE instructions, and you can still access the member with the array operator without problems.
On a 64-bit system the compiler might align to 8-byte boundaries. Also if you want a generic vector class you can't assume anything like that. Also for indexing with x,y,z/[0,1,2] all union tricks are out if you want to support UDTs. P.S. there is a mailing list that might be of interest to some in this discussion. http://sourceforge.net/mailarchive/forum.php?forum_id=49012

Olivier Grant wrote:
Well due to the fact that floats are represented on 4 bytes, there shouldn't be any padding involved. Padding normally occures when certain member variables of a structure require certain alignment constraints or just for efficiency, but this shouldn't occur with a vector class (at least that is my understanding).
Why assume the type's will be floats ? There's a number of situations where doubles, fixed point or some lossless representation would be preferable, any solution that doesn't allow this isn't a serious vector library imo. Typedefs though should be provided for all the common cases (floats / doubles) for ease of use. cheers Martin

Hi Guys, I am using VC6, boost-1.33.1, and I've compiled the regex lib mt-s and ms-sgd It works when I have used mt-s in the release, however, when it comes to the debug mode. Any regex call will prompt me a vc++ "debug error" From my program console, it shows Assertion failed: r == 1 << 8, file E:\boost_1_33_1_beta\boost_1_33_1 \libs\regex\build\../src/w32_regex_traits.cpp, line 108 and then the program terminated with "abnormal program termination" error message I've tested this by taken out all regex related variables, function calls. Then the debug version of my program works! Anybody know what this really mean? I wonder if this is because of the issue during lib compilation. HCan anyone please give me a helping hand? I am really appreciate yours help. Best regards, Kit

tikcireviva <tikcireviva@yahoo.com.hk> writes:
Hi Guys,
I am using VC6, boost-1.33.1, and I've compiled the regex lib mt-s and ms-sgd It works when I have used mt-s in the release, however, when it comes to the debug mode. Any regex call will prompt me a vc++ "debug error"
From my program console, it shows Assertion failed: r == 1 << 8, file E:\boost_1_33_1_beta\boost_1_33_1 \libs\regex\build\../src/w32_regex_traits.cpp, line 108 and then the program terminated with "abnormal program termination" error message
I've tested this by taken out all regex related variables, function calls. Then the debug version of my program works!
Anybody know what this really mean? I wonder if this is because of the issue during lib compilation. HCan anyone please give me a helping hand? I am really appreciate yours help.
Kit, start a new thread intead of replying to an existing one ("Geometry/Vector Lib") if you want your post to be noticed. -- Dave Abrahams Boost Consulting www.boost-consulting.com

tikcireviva wrote:
Hi Guys,
I am using VC6, boost-1.33.1, and I've compiled the regex lib mt-s and ms-sgd It works when I have used mt-s in the release, however, when it comes to the debug mode. Any regex call will prompt me a vc++ "debug error"
From my program console, it shows Assertion failed: r == 1 << 8, file E:\boost_1_33_1_beta\boost_1_33_1 \libs\regex\build\../src/w32_regex_traits.cpp, line 108 and then the program terminated with "abnormal program termination" error message
I've tested this by taken out all regex related variables, function calls. Then the debug version of my program works!
Anybody know what this really mean? I wonder if this is because of the issue during lib compilation. HCan anyone please give me a helping hand? I am really appreciate yours help.
This is a known issue in 1.33.1 when running on a Chinese (and possibly other MBCS) locale. I believe it's fixed in cvs. See https://sourceforge.net/tracker/?func=detail&atid=207586&aid=1358740&group_id=7586 and the patch is: http://boost.cvs.sourceforge.net/boost/boost/libs/regex/src/w32_regex_traits.cpp?r1=1.44&r2=1.44.2.1 HTH, John.

"Martin Slater" <mslater@netspace.net.au> wrote in message news:4514AB08.5020406@netspace.net.au...
Olivier Grant wrote:
Well due to the fact that floats are represented on 4 bytes, there shouldn't be any padding involved. Padding normally occures when certain member variables of a structure require certain alignment constraints or just for efficiency, but this shouldn't occur with a vector class (at least that is my understanding).
Why assume the type's will be floats ? There's a number of situations where doubles, fixed point or some lossless representation would be preferable, any solution that doesn't allow this isn't a serious vector library imo. Typedefs though should be provided for all the common cases (floats / doubles) for ease of use.
FWIW a boost::array is a valid fusion sequence, as OTOH is a tuple making Fusion: http://spirit.sourceforge.net/dl_more/fusion_v2/libs/fusion/doc/html/index.h... a good choice as a basis for working with vectors and matrices of arbitrary types. With a boost::array as the element type of a matrix it is relatively trivial to access a fusion style matrix via the familiar matrix[R][C] syntax. Fusion also provides very powerful compile time ( and run time) facilities and is well worth investigating for anyone contemplating a state of the art linear algebra library. regards Andy Little

"Olivier Grant" <olivier.grant@gmail.com> wrote:
Hi,
I have written a bit of code to handle geometric vectors in a generic way, abstracting their dimension. The idea behind this code is to be able to apply one operation between two vectors, or a vector and a scalar, whatever their dimension, and writing it in an expandable way without having to modify any manipulation functions if a new geometric vector class is created. The other advantage is that the resulting assembly code is just as fast as if the functions had all been explicitly written.
Does this hold true if the equations get complicated (e.g. products of products)?
Right now I have three simple vector classes - ranging from vector2d to vector4d - that are not templetized since I like the idea of being able to access coordinates directly by their name
vector3d vec; vec.x += 10.0f;
to give you an example of the syntax, here is how you would add two vectors of different dimensions :
vector2d v1(1.0f, 2.0f); vector3d v2(-1.0f, 3.0f, 2.0f); vector4d res;
vector_add(v1, v2, res); /* res now contains (0.0f, 5.0f, 2.0f, 1.0f) */
This is a bit clunky. What about using the operator+() and operator=()?
the result is determined by the dimension of the third vector passed to vector_add. v1 is auto-promoted to act like a vector3d.
This seems wrong. If I want to add a vector2d to a vector3d, then I should have to do it manually. Otherwise, it should be a type error.
v2 does not change. res gets (v1.x + v2.x, v1.y + v2.y, v1.z + v2.z, default_w_value).
I didn't seem to find any information on a lib currently under development that provides geometric vector manipulation in that way - maybe apart from uBLAS - so I thought I would share this if anyone seems to be interested.
What are the advantages of this library over tvmet[1]? Cheers, Walter Landry wlandry@ucsd.edu [1] http://tvmet.sourceforge.net/

On 9/20/06, Olivier Grant <olivier.grant@gmail.com> wrote:
Right now I have three simple vector classes - ranging from vector2d to vector4d - that are not templetized since I like the idea of being able to access coordinates directly by their name
vector3d vec; vec.x += 10.0f;
Thanks to SFINAE you can do that for the general case, so long as you don't mind vec.x() += 10; Which I don't think is a great hardship. In a math::vector<T,N>, for example, you'd have code like this: boost::enable_if_c< N >= 1, T& > x() { return v[0]; } boost::enable_if_c< N >= 2, T& > y() { return v[1]; } boost::enable_if_c< N >= 3, T& > z() { return v[2]; } boost::enable_if_c< N >= 4, T& > w() { return v[3]; } I've written a fully-templated math::vector class that you can find at http://gpwiki.org/index.php/C_plus_plus:Tutorials:TemplateVector (not using boost though, so it does a bad form of STATIC_ASSERT instead of the enable_if ). That being said, why can't you use uBLAS ( http://boost.org/libs/numeric/ublas/doc/vector.htm ) or some other premade library? Other people have already written heavily-optimized ones, using expression templates and such to keep the nice syntax without adding inefficiencies. (No need for a 3-argument add function, for example.) ~ Scott McMurray

Olivier Grant said: (by the date of Wed, 20 Sep 2006 17:25:39 +0100)
Hi,
I have written a bit of code to handle geometric vectors in a generic way,
have a look at MTL4 (not finished yet) http://osl.iu.edu/research/mtl/ I should subscribe to their maling list... :) will do. http://www.osl.iu.edu/mailman/listinfo.cgi/mtl4 -- Janek Kozicki |

"Janek Kozicki" <janek_listy@wp.pl> wrote in message news:20060920202105.4d5df88c@absurd...
Olivier Grant said: (by the date of Wed, 20 Sep 2006 17:25:39 +0100)
Hi,
I have written a bit of code to handle geometric vectors in a generic way,
have a look at MTL4 (not finished yet)
http://osl.iu.edu/research/mtl/
I should subscribe to their maling list... :) will do.
Lets look at the checklist: code : none examples : none documentation : none tests : none list response : none looks like vapourware to me ! OTOH: http://tinyurl.com/qp56p http://sourceforge.net/projects/quan/ regards Andy Little

"Andy Little" <andy@servocomm.freeserve.co.uk> wrote in message news:ef1qds$4t1$1@sea.gmane.org...
"Janek Kozicki" <janek_listy@wp.pl> wrote in message news:20060920202105.4d5df88c@absurd...
Olivier Grant said: (by the date of Wed, 20 Sep 2006 17:25:39 +0100)
Hi,
I have written a bit of code to handle geometric vectors in a generic way,
have a look at MTL4 (not finished yet)
http://osl.iu.edu/research/mtl/
I should subscribe to their maling list... :) will do.
Lets look at the checklist:
code : none examples : none documentation : none tests : none list response : none
looks like vapourware to me !
OTOH:
Oh aye. To appreciate the code, you will need to download the Quan CVS. In light of comments from the fusion authors, the dot product code has become lazier, but contradictarily, weirdly, also faster. regards Andy Little

"Andy Little" <andy@servocomm.freeserve.co.uk> wrote in message news:ef1qds$4t1$1@sea.gmane.org...
"Janek Kozicki" <janek_listy@wp.pl> wrote in message news:20060920202105.4d5df88c@absurd...
Olivier Grant said: (by the date of Wed, 20 Sep 2006 17:25:39 +0100)
Hi,
I have written a bit of code to handle geometric vectors in a generic way,
have a look at MTL4 (not finished yet)
http://osl.iu.edu/research/mtl/
I should subscribe to their maling list... :) will do.
Lets look at the checklist:
code : none examples : none documentation : none tests : none list response : none
looks like vapourware to me !
Or am I missing something that everybody else seems to know about ? regards Andy Little

created. The other advantage is that the resulting assembly code is just as fast as if the functions had all been explicitly written.
even if that assembly is optimised sse?
vector2d v1(1.0f, 2.0f); vector3d v2(-1.0f, 3.0f, 2.0f); vector4d res;
vector_add(v1, v2, res); /* res now contains (0.0f, 5.0f, 2.0f, 1.0f) */
I've been bitten too many times using a library that does just this, if I want to change a n dimensional vector to any other dimension the added values should be explicitly provided. Optimised versions that implicitly assume a value should be named accordingly so their use is obvious. Also using a c style interface to make the actual maths even more impenetrable seems like a bad idea. There was a very long discussion about a vector library aimed towards game development on the sweng mailing list recently (http://lists.midnightryder.com/pipermail/sweng-gamedev-midnightryder.com/) which you may find useful. cheers Martin

Hi, I would like to read the thread you're talking about, but I can't seem to find it. Would you have a direct link or its name ? Thanks, Olivier. On 9/21/06, Martin Slater < mslater@netspace.net.au> wrote:
created. The other advantage is that the resulting assembly code is just as fast as if the functions had all been explicitly written.
even if that assembly is optimised sse?
vector2d v1(1.0f, 2.0f); vector3d v2(-1.0f, 3.0f, 2.0f); vector4d res;
vector_add(v1, v2, res); /* res now contains (0.0f, 5.0f, 2.0f, 1.0f) */
I've been bitten too many times using a library that does just this, if I want to change a n dimensional vector to any other dimension the added values should be explicitly provided. Optimised versions that implicitly assume a value should be named accordingly so their use is obvious. Also using a c style interface to make the actual maths even more impenetrable seems like a bad idea.
There was a very long discussion about a vector library aimed towards game development on the sweng mailing list recently (http://lists.midnightryder.com/pipermail/sweng-gamedev-midnightryder.com/ ) which you may find useful.
cheers
Martin _______________________________________________ Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost
participants (18)
-
Andy Little
-
David Abrahams
-
Frank Birbacher
-
Geoffrey Irving
-
Janek Kozicki
-
Jason Hise
-
John Maddock
-
Marcus Lindblom
-
Martin Bonner
-
Martin Slater
-
me22
-
Michael Fawcett
-
Michael Marcin
-
Olivier Grant
-
Sohail Somani
-
Theodore Papadopoulo
-
tikcireviva
-
Walter Landry