# Operators for 3D Vector Mathematics

• 01-31-2003
Anarchist
Operators for 3D Vector Mathematics
I'm writing a graphics program that uses 3D vectors, I have an existing library that I've written that already contains all the code for vector manipiulation but it was written in C using a struct to define a vector and funtions to manipulate them.
I now have a Vector class as I'm writing in C++ and rather than have to call a funtion which makes the code less readable I'd like to overload the operators, the only problem is I dont know how to write the function headers for the operator overloading for what I need or if its possable for some of it. this is whats needed

Vector + Vector = Vector
Vector - Vector = Vector
Vector x Vector = Vector (Cross product)
Vector . Vector = float (Dot product)
Vector * float = Vector (Scaling)
Vector = Vector

also if I'm using pointers to the vector class would I need to dereference the pointer to use the operators?

I'm not to sure how operator over loading works but would a line like this

Code:

`CVector operator + (CVector &v2)`
be processed as
Code:

`return type =  this + v2`
• 01-31-2003
hk_mp5kpdw
Unless I'm mistaken, the STL already has this covered. Look up info on the valarray templated object. There are a few problems with using it, the people who introduced the concept to the C++ standard library left the committee before the standard was finished so it tends to have an unpolished feel, but hey... you can work around that can't you?
• 01-31-2003
FillYourBrain
Re: Operators for 3D Vector Mathematics
Quote:

Originally posted by Anarchist
also if I'm using pointers to the vector class would I need to dereference the pointer to use the operators?
yup, that's about right. use references when you can though. for instance:

CVector *myptr;
//some stuff to get the pointer
CVector & alias = *myptr;

something = alias + blah;

since you have alias as a reference instead of a pointer you can use the thing without dereferencing explicitly.

of course you could always do a bunch of other things...

myptr->operator+() can be called
(*myptr) + blah //you already knew that.
• 01-31-2003
Anarchist
The STL valarray looked far too complicated, and what I did understand didnt apear to do what I wanted. I'm not sure which would have been easiest changing my existing code to use a new type or writing the extra bits I need now ( I have a very bad programming style - I write bits as I need them) my vectors are defined and have constructors and the accessors I needed ( probably a bad idea as theyre just getting on my nerves I should have just ignored my OOP tutor when he said all member variables should be private with accessors) but I havnt made the actual manipulation code yet as I've only just got to the point in my program where I need it. So it looks like I'll have to rake out my old program n use the functions or do the same and overload the operators.

Thanks for the tip hk_mp5kpdw if I ever manage to understand the STL or templates in general I may use the valarray in a later program. I think I've missed out on a lot of what makes c++ by learning it from the appendix of a windows games book and what 've managed to pick up from the MSVC++ documentation

Thanks FillYourBrain for explaining that all the sources I've seen have never really covered that, I'm begingin to think that I dont really need the massive amout of pointers that I use in my programs
• 01-31-2003
grib
valarray is not exactly a replacement for a 3d vector class, particularly your own. There is a paper on the web by the guy who wrote it, an interesting read. To overload operators (and you can't overload . sorry) the usual way is to first overload the assignment version.

Code:

```class Vector { ...     Vector & operator += (const Vector &rhs)     {         x += rhs.x; y += rhs.y; z = rhs.z; // or x() += rhs.x(); y() += rhs.y(); z() += rhs.z();         return *this;     } }; // then, for sugar, make a binary version inline Vector operator +(const Vector &lhs, const Vector &rhs) {     return Vector(lhs)+=rhs; }```
The binary + invokes the copy constructor at least once, possibly twice. There is a nifty trick in The C++ Programming Language section 22.4.7 that details how to reduce temporaries and copying.

Fill your brain, holding references to pointers is almost always bad news. The assembly generated will be identical but you now have a way to unexpectedly delete something held in a reference.

As to public members/accessors don't worry about it. The main reason you want to make something private is so that you can change it later. Common ways to do 3Dvector are to either have explicit public members x,y,z or something like this
Code:

```class vec3D {     enum {xpos=0, ypos=1, zpos=2}; public:     vec3D(const vec3D &vec) {         memcpy(v,vec.v,sizeof(v));     }     typedef double scalar;     scalar & x() {reutrn v[xpos];}        scalar & y() {reutrn v[ypos];}        scalar & z() {reutrn v[zpos];}    private:     scalar v[3]; };```
Some things may be faster in terms of v, but you still have easily readable operations.
• 01-31-2003
FillYourBrain
references ARE pointers. if you've done the appropriate checks and are careful (as you must be with all pointers) you will not have an issue. as far as the aliasing scenario I mentioned, it's an extreme case and probably not necessary when you can just pass a reference into the function to begin with. References are far cleaner syntax than pointers most of the time.
• 01-31-2003
Anarchist
Thanks for the tips, I shoudl be able to get things going now
• 01-31-2003
grib
It's a style thing I guess, but to me a reference to a value addressed by a pointer cleans up things that should be ugly. If you need the functionality of the pointer then use it, if you need an alias use a reference. Keep in mind also that while a reference CAN be a pointer, the comiler is going to do it's level best to avoid doing so.

int i=7;
int *p = &i;
int &r = i;
int a = *p + 3; // generates deref
int b = r + 3; // can generate identical code to i + 3;
int &r2 = *p;
int c = r2 + 3; // will almost always deref, but looks normal
• 01-31-2003
Anarchist
Same subject Different problem
when compiling my code I get the error
Quote:

error C2679: binary '*' : no operator defined which takes a right-hand operand of type 'const float' (or there is no acceptable conversion)
the 1 line of code that causes this is infact the second line that uses vector scaling
Code:

```                        *polyNormal=( (*Triangle->GetVertex(FIRST)->GetNormal()) * (1-(alpha+beta)) )+                                 ((*Triangle->GetVertex(SECOND)->GetNormal()) * alpha )+                                 ((*Triangle->GetVertex(THIRD)->GetNormal()) * beta);```
this basically boils down to vector= (vector * float) +(vector * float) +(vector * float)
at first glance you'd think I havnt written the code for the operator but an earlier line that uses it compiles fine

Code:

`                *position = *m_Start + (*m_Direction * t);`
this being Vector = Vector + (Vector * float)
I can't see why these lines of code should be treated differently
could the problem be because I use function calls to get a pointer to the Vector(GetNormal) and then dereference this?

Interestingly enough if I replace the 1-(alpha+beta) with a variable of type float it works, could anyone explain this behaviour?

if it helps the operator for scaling id defined as
Code:

`        CVector operator * (float &val); //scale`
• 01-31-2003
grib
The short answer is just use
CVector operator * (float val); //scale
or possibly
CVector operator * (const float &val); //scale
In general pass normal scalar plain old data(float,char,int) by value and classes or complicated stuff as a reference to const.

The reason your compiler is complaining is because you cannot take a non-const reference to a temporary. (1-(alpha+beta)) results in a temporary float being generated, two actually, one for the result of alpha+beta and another to hold 1 minus the previous temporary.
• 01-31-2003
Silvercord
Hey anarchist I dont' know how interested you are in math, nor do I know what you already know, but this is a really good book dealing with all aspects of 3d computer programming. It assumes trig and calculus experience, however. I bought this book a few days ago and have been reading through it and I am very satisfied with its content (I estimate I'll personally be reading it for a year before I can say I have good command of all the content). It explains everything in as much detail you could ask for, contains appendices for reference (i.e important trig stuff such as law of sines and cosines and all of the other basic stuff) and shows simple implementations using opengl (and I'm not sure what language, actually looks like assembly because it says 'mov' in there :))

http://www.amazon.ca/exec/obidos/ASI...152163-2461153

Anyway read the book description and you'll find it contains everything you'd want to know and im going to stfu now